C# Class kOS.Safe.Execution.CPU

Inheritance: ICpu
显示文件 Open project: KSP-KOS/KOS

Public Methods

Method Description
AddTrigger ( int triggerFunctionPointer ) : void
AddVariable ( kOS.Safe.Execution.Variable variable, string identifier, bool local, bool overwrite = false ) : void

Make a new variable at either the local depth or the global depth depending. throws exception if it already exists as a boundvariable at the desired scope level, unless overwrite = true.

AssertValidDelegateCall ( IUserDelegate userDelegate ) : void

Throw exception if the user delegate is not one the CPU can call right now.

Boot ( ) : void
BreakExecution ( bool manual ) : void
BuiltInExists ( string functionName ) : bool
CPU ( SafeSharedObjects shared ) : System
CallBuiltinFunction ( string functionName ) : void
Dispose ( ) : void
DumpStack ( ) : string
DumpVariables ( ) : string
GetCallTrace ( ) : List

Return the subroutine call trace of how the code got to where it is right now.

GetCodeFragment ( int contextLines ) : List
GetCurrentClosure ( ) : List

Build a clone of the current state of the scope stack, for the sake of capturing a closure.

GetCurrentOpcode ( ) : Opcode
GetInterpreterContext ( ) : IProgramContext
GetOpcodeAt ( int instructionPtr ) : Opcode
GetStackSize ( ) : int
GetStructureEncapsulated ( Structure testValue, bool barewordOkay = false ) : Structure

Identical to GetValue(), except that it guarantees the return value is either already a Structure, or it converts it into a Structure if it's a primitive. It bombs out with an exception if it can't be converted thusly.
Use this in places where the stack value *must* come out as an encapsulated value and something has gone seriously wrong if it can't. This applies to cases where you are attempting to store its value inside another user's variable, mostly.
Hypothetically this should never really be required, as the value is coming FROM a user varible in the first place.

GetValue ( object testValue, bool barewordOkay = false ) : object

Given a value which may or may not be a variable name, return the value back. If it's not a variable, return it as-is. If it's a variable, look it up and return that.

IdentifierExistsInScope ( string identifier ) : bool

Test if an identifier is a variable you can get the value of at the moment (var name exists and is in scope). Return true if you can, false if you can't.

KOSFixedUpdate ( double deltaTime ) : void
MakeUserDelegate ( int entryPoint, bool withClosure ) : IUserDelegate

Build a delegate call for the given function entry point, in which it will capture a closure of the current runtime scoping state to be used when that function gets called later by OpcodeCall:

MoveStackPointer ( int delta ) : void
PeekRaw ( int digDepth, bool &checkOkay ) : object

Peek at a value atop the stack without popping it, and without evaluating it to get the variable's value. (i.e. if the thing in the stack is $foo, and the variable foo has value 5, you'll get the string "$foo" returned, not the integer 5).

PeekStructureEncapsulated ( int digDepth, bool barewordOkay = false ) : Structure

Identical to PeekValue(), except that it guarantees the return value is either already a Structure, or it converts it into a Structure if it's a primitive. It bombs out with an exception if it can't be converted thusly.
Use this in places where the stack value *must* come out as an encapsulated value and something has gone seriously wrong if it can't. This applies to cases where you are attempting to store its value inside a user's variable, mostly.

PeekValue ( int digDepth, bool barewordOkay = false ) : object

Peek at a value atop the stack without popping it, and if it's a variable name then get its value, else just return it as it is.

NOTE: Evaluating variables when you don't really need to is pointlessly expensive, as it needs to walk the scoping stack to exhaust a search. If you don't need to evaluate variables, then consider using PeekRaw() instead.

PeekValueEncapsulated ( int digDepth, bool barewordOkay = false ) : object

Identical to PeekStructureEncapsulated(), except that it doesn't complain if the result can't be converted to a Structure. It's acceptable for it to not be a Structure, in which case the original object is returned as-is.
Use this in places where the stack value *should* come out as an encapsulated value if it can, but there are some valid cases where it might not be.

PopAboveStack ( int howMany ) : object

Pop one or more things from the secret "over" stack, only returning the finalmost thing popped. (i.e if you pop 3 things then you get: pop once and throw away, pop again and throw away, pop again and return the popped thing.)

PopStack ( ) : object
PopStructureEncapsulated ( bool barewordOkay = false ) : Structure

Identical to PopValue(), except that it guarantees the return value is either already a Structure, or it converts it into a Structure if it's a primitive. It bombs out with an exception if it can't be converted thusly.
Use this in places where the stack value *must* come out as an encapsulated value and something has gone seriously wrong if it can't. This applies to cases where you are attempting to store its value inside a user's variable, mostly.

PopValue ( bool barewordOkay = false ) : object

Pop a value off the stack, and if it's a variable name then get its value, else just return it as it is.

PopValueEncapsulated ( bool barewordOkay = false ) : object

Identical to PopStructureEncapsulated(), except that it doesn't complain if the result can't be converted to a Structure. It's acceptable for it to not be a Structure, in which case the original object is returned as-is.
Use this in places where the stack value *should* come out as an encapsulated value if it can, but there are some valid cases where it might not be.

PushAboveStack ( object thing ) : void

Push a single thing onto the secret "over" stack.

PushStack ( object item ) : void
RemoveTrigger ( int triggerFunctionPointer ) : void
RemoveVariable ( string identifier ) : void

Removes a variable, following current scoping rules, removing the innermost scope of the variable that is found.

If the variable cannot be found, it fails silently without complaint.

ResetStatistics ( ) : void
RunProgram ( List program ) : void
RunProgram ( List program, bool silent ) : void
SelectAutopilotMode ( string autopilotMode ) : void
SetGlobal ( string identifier, object value ) : void

Make a new global variable at the localmost scoping level and give it a starting value, or overwrite an existing variable at the localmost level with a starting value.

This does NOT scan up the scoping stack like SetValue() does. It operates at the global level only.

SetNewLocal ( string identifier, object value ) : void

Try to make a new local variable at the localmost scoping level and give it a starting value. It errors out of there is already one there by the same name.

This does NOT scan up the scoping stack like SetValue() does. It operates at the local level only.

This is the normal way to make a new local variable. You cannot make a local variable without attempting to give it a value.

SetValue ( string identifier, object value ) : void

Try to set the value of the identifier at the localmost level possible, by scanning up the scope stack to find the local-most level at which the identifier is a variable, and assigning it the value there.

If no such value is found, all the way up to the global level, then it resorts to making a global variable with the name and using that.

This is the normal way to make a new global variable. You cannot make a global variable without attempting to give it a value.

SetValueExists ( string identifier, object value ) : void

Try to set the value of the identifier at the localmost level possible, by scanning up the scope stack to find the local-most level at which the identifier is a variable, and assigning it the value there.

If no such value is found, an error is thrown. It only stores into variables that already exist, refusing to create new variables.

StartCompileStopwatch ( ) : void
StatisticsDump ( bool doProfiling ) : string
StopCompileStopwatch ( ) : void
SwitchToProgramContext ( ) : IProgramContext
ToggleFlyByWire ( string paramName, bool enabled ) : void
VariableIsRemovable ( Variable variable ) : bool
YieldProgram ( YieldFinishedDetector yieldTracker ) : void

Call when you want to suspend execution of the Opcodes until some future condition becomes true. The CPU will call yieldTracker.Begin() right away, and then after that call yieldTracker.IsFinished() again and again until it returns true. Until IsFinished() returns true, the CPU will not advance any further into the program in its current "mode". Note that the CPU will track "trigger" and "mainline" code separately for this purpose. Waiting in mainline code will still allow triggers to run.

Private Methods

Method Description
AbortAllYields ( ) : void
CalculateProfileResult ( ) : void
ContinueExecution ( bool doProfiling ) : void
ExecuteInstruction ( IProgramContext context, bool doProfiling ) : bool
GetNestedDictionary ( int peekDepth ) : VariableScope

Gets the dictionary N levels of nesting down the dictionary stack, where zero is the current localmost level. Never errors out or fails. If N is too large you just end up with the global scope dictionary. Does not allow the walk to go past the start of the current function scope.

GetNestedDictionary ( string identifier, List searchReport = null ) : VariableScope

Gets the dictionary that contains the given identifier, starting the search at the local level and scanning the scopes upward all the way to the global dictionary.
Does not allow the walk to use scope frames that were not directly in this scope's lexical chain. It skips over scope frames from other branches of the parse tree. (i.e. if a function calls a function elsewhere).
Returns null when no hit was found.

GetOrCreateVariable ( string identifier ) : Variable

Get the value of a variable or create it at global scope if not found.

GetVariable ( string identifier, bool barewordOkay = false, bool failOkay = false ) : Variable

Get the variable's contents, performing a lookup through all nesting levels up to global.

IsYielding ( ) : bool
PopContext ( ) : void
PopFirstContext ( ) : void
PostUpdateBindings ( ) : void
PreUpdateBindings ( ) : void
PrintStatistics ( ) : void
ProcessTriggers ( ) : void
PushContext ( ProgramContext context ) : void
PushInterpreterContext ( ) : void
RestorePointers ( ) : void
SaveAndClearPointers ( ) : void
SkipCurrentInstructionId ( ) : void

Method Details

AddTrigger() public method

public AddTrigger ( int triggerFunctionPointer ) : void
triggerFunctionPointer int
return void

AddVariable() public method

Make a new variable at either the local depth or the global depth depending. throws exception if it already exists as a boundvariable at the desired scope level, unless overwrite = true.
public AddVariable ( kOS.Safe.Execution.Variable variable, string identifier, bool local, bool overwrite = false ) : void
variable kOS.Safe.Execution.Variable variable to add
identifier string name of variable to add
local bool true if you want to make it at local depth
overwrite bool true if it's okay to overwrite an existing variable
return void

AssertValidDelegateCall() public method

Throw exception if the user delegate is not one the CPU can call right now.
thrown if the cpu is in a state where it can't call this delegate.
public AssertValidDelegateCall ( IUserDelegate userDelegate ) : void
userDelegate IUserDelegate The userdelegate being checked
return void

Boot() public method

public Boot ( ) : void
return void

BreakExecution() public method

public BreakExecution ( bool manual ) : void
manual bool
return void

BuiltInExists() public method

public BuiltInExists ( string functionName ) : bool
functionName string
return bool

CPU() public method

public CPU ( SafeSharedObjects shared ) : System
shared SafeSharedObjects
return System

CallBuiltinFunction() public method

public CallBuiltinFunction ( string functionName ) : void
functionName string
return void

Dispose() public method

public Dispose ( ) : void
return void

DumpStack() public method

public DumpStack ( ) : string
return string

DumpVariables() public method

public DumpVariables ( ) : string
return string

GetCallTrace() public method

Return the subroutine call trace of how the code got to where it is right now.
public GetCallTrace ( ) : List
return List

GetCodeFragment() public method

public GetCodeFragment ( int contextLines ) : List
contextLines int
return List

GetCurrentClosure() public method

Build a clone of the current state of the scope stack, for the sake of capturing a closure.
public GetCurrentClosure ( ) : List
return List

GetCurrentOpcode() public method

public GetCurrentOpcode ( ) : Opcode
return kOS.Safe.Compilation.Opcode

GetInterpreterContext() public method

public GetInterpreterContext ( ) : IProgramContext
return IProgramContext

GetOpcodeAt() public method

public GetOpcodeAt ( int instructionPtr ) : Opcode
instructionPtr int
return Opcode

GetStackSize() public method

public GetStackSize ( ) : int
return int

GetStructureEncapsulated() public method

Identical to GetValue(), except that it guarantees the return value is either already a Structure, or it converts it into a Structure if it's a primitive. It bombs out with an exception if it can't be converted thusly.
Use this in places where the stack value *must* come out as an encapsulated value and something has gone seriously wrong if it can't. This applies to cases where you are attempting to store its value inside another user's variable, mostly.
Hypothetically this should never really be required, as the value is coming FROM a user varible in the first place.
public GetStructureEncapsulated ( Structure testValue, bool barewordOkay = false ) : Structure
testValue Structure the object which might be a variable name
barewordOkay bool /// Is this a case in which it's acceptable for the /// variable not to exist, and if it doesn't exist then the variable name itself /// is the value? ///
return Structure

GetValue() public method

Given a value which may or may not be a variable name, return the value back. If it's not a variable, return it as-is. If it's a variable, look it up and return that.
public GetValue ( object testValue, bool barewordOkay = false ) : object
testValue object the object which might be a variable name
barewordOkay bool /// Is this a case in which it's acceptable for the /// variable not to exist, and if it doesn't exist then the variable name itself /// is the value? ///
return object

IdentifierExistsInScope() public method

Test if an identifier is a variable you can get the value of at the moment (var name exists and is in scope). Return true if you can, false if you can't.
public IdentifierExistsInScope ( string identifier ) : bool
identifier string
return bool

KOSFixedUpdate() public method

public KOSFixedUpdate ( double deltaTime ) : void
deltaTime double
return void

MakeUserDelegate() public method

Build a delegate call for the given function entry point, in which it will capture a closure of the current runtime scoping state to be used when that function gets called later by OpcodeCall:
public MakeUserDelegate ( int entryPoint, bool withClosure ) : IUserDelegate
entryPoint int Integer location in memory to jump to to start the call
withClosure bool Should the closure be captured for this delegate or ignored
return IUserDelegate

MoveStackPointer() public method

public MoveStackPointer ( int delta ) : void
delta int
return void

PeekRaw() public method

Peek at a value atop the stack without popping it, and without evaluating it to get the variable's value. (i.e. if the thing in the stack is $foo, and the variable foo has value 5, you'll get the string "$foo" returned, not the integer 5).
public PeekRaw ( int digDepth, bool &checkOkay ) : object
digDepth int Peek at the element this far down the stack (0 means top, 1 means just under the top, etc)
checkOkay bool Tells you whether or not the stack was exhausted. If it's false, then the peek went too deep.
return object

PeekStructureEncapsulated() public method

Identical to PeekValue(), except that it guarantees the return value is either already a Structure, or it converts it into a Structure if it's a primitive. It bombs out with an exception if it can't be converted thusly.
Use this in places where the stack value *must* come out as an encapsulated value and something has gone seriously wrong if it can't. This applies to cases where you are attempting to store its value inside a user's variable, mostly.
public PeekStructureEncapsulated ( int digDepth, bool barewordOkay = false ) : Structure
digDepth int Peek at the element this far down the stack (0 means top, 1 means just under the top, etc)
barewordOkay bool Is this a context in which it's acceptable for /// a variable not existing error to occur (in which case the identifier itself /// should therefore become a string object returned)?
return Structure

PeekValue() public method

Peek at a value atop the stack without popping it, and if it's a variable name then get its value, else just return it as it is.

NOTE: Evaluating variables when you don't really need to is pointlessly expensive, as it needs to walk the scoping stack to exhaust a search. If you don't need to evaluate variables, then consider using PeekRaw() instead.
public PeekValue ( int digDepth, bool barewordOkay = false ) : object
digDepth int Peek at the element this far down the stack (0 means top, 1 means just under the top, etc)
barewordOkay bool Is this a context in which it's acceptable for /// a variable not existing error to occur (in which case the identifier itself /// should therefore become a string object returned)?
return object

PeekValueEncapsulated() public method

Identical to PeekStructureEncapsulated(), except that it doesn't complain if the result can't be converted to a Structure. It's acceptable for it to not be a Structure, in which case the original object is returned as-is.
Use this in places where the stack value *should* come out as an encapsulated value if it can, but there are some valid cases where it might not be.
public PeekValueEncapsulated ( int digDepth, bool barewordOkay = false ) : object
digDepth int Peek at the element this far down the stack (0 means top, 1 means just under the top, etc)
barewordOkay bool Is this a context in which it's acceptable for /// a variable not existing error to occur (in which case the identifier itself /// should therefore become a string object returned)?
return object

PopAboveStack() public method

Pop one or more things from the secret "over" stack, only returning the finalmost thing popped. (i.e if you pop 3 things then you get: pop once and throw away, pop again and throw away, pop again and return the popped thing.)
public PopAboveStack ( int howMany ) : object
howMany int
return object

PopStack() public method

public PopStack ( ) : object
return object

PopStructureEncapsulated() public method

Identical to PopValue(), except that it guarantees the return value is either already a Structure, or it converts it into a Structure if it's a primitive. It bombs out with an exception if it can't be converted thusly.
Use this in places where the stack value *must* come out as an encapsulated value and something has gone seriously wrong if it can't. This applies to cases where you are attempting to store its value inside a user's variable, mostly.
public PopStructureEncapsulated ( bool barewordOkay = false ) : Structure
barewordOkay bool Is this a context in which it's acceptable for /// a variable not existing error to occur (in which case the identifier itself /// should therefore become a string object returned)?
return Structure

PopValue() public method

Pop a value off the stack, and if it's a variable name then get its value, else just return it as it is.
public PopValue ( bool barewordOkay = false ) : object
barewordOkay bool Is this a context in which it's acceptable for /// a variable not existing error to occur (in which case the identifier itself /// should therefore become a string object returned)?
return object

PopValueEncapsulated() public method

Identical to PopStructureEncapsulated(), except that it doesn't complain if the result can't be converted to a Structure. It's acceptable for it to not be a Structure, in which case the original object is returned as-is.
Use this in places where the stack value *should* come out as an encapsulated value if it can, but there are some valid cases where it might not be.
public PopValueEncapsulated ( bool barewordOkay = false ) : object
barewordOkay bool Is this a context in which it's acceptable for /// a variable not existing error to occur (in which case the identifier itself /// should therefore become a string object returned)?
return object

PushAboveStack() public method

Push a single thing onto the secret "over" stack.
public PushAboveStack ( object thing ) : void
thing object
return void

PushStack() public method

public PushStack ( object item ) : void
item object
return void

RemoveTrigger() public method

public RemoveTrigger ( int triggerFunctionPointer ) : void
triggerFunctionPointer int
return void

RemoveVariable() public method

Removes a variable, following current scoping rules, removing the innermost scope of the variable that is found.

If the variable cannot be found, it fails silently without complaint.
public RemoveVariable ( string identifier ) : void
identifier string varible to remove.
return void

ResetStatistics() public method

public ResetStatistics ( ) : void
return void

RunProgram() public method

public RunProgram ( List program ) : void
program List
return void

RunProgram() public method

public RunProgram ( List program, bool silent ) : void
program List
silent bool
return void

SelectAutopilotMode() public method

public SelectAutopilotMode ( string autopilotMode ) : void
autopilotMode string
return void

SetGlobal() public method

Make a new global variable at the localmost scoping level and give it a starting value, or overwrite an existing variable at the localmost level with a starting value.

This does NOT scan up the scoping stack like SetValue() does. It operates at the global level only.
public SetGlobal ( string identifier, object value ) : void
identifier string variable name to attempt to store into
value object value to put into it
return void

SetNewLocal() public method

Try to make a new local variable at the localmost scoping level and give it a starting value. It errors out of there is already one there by the same name.

This does NOT scan up the scoping stack like SetValue() does. It operates at the local level only.

This is the normal way to make a new local variable. You cannot make a local variable without attempting to give it a value.
public SetNewLocal ( string identifier, object value ) : void
identifier string variable name to attempt to store into
value object value to put into it
return void

SetValue() public method

Try to set the value of the identifier at the localmost level possible, by scanning up the scope stack to find the local-most level at which the identifier is a variable, and assigning it the value there.

If no such value is found, all the way up to the global level, then it resorts to making a global variable with the name and using that.

This is the normal way to make a new global variable. You cannot make a global variable without attempting to give it a value.
public SetValue ( string identifier, object value ) : void
identifier string variable name to attempt to store into
value object value to put into it
return void

SetValueExists() public method

Try to set the value of the identifier at the localmost level possible, by scanning up the scope stack to find the local-most level at which the identifier is a variable, and assigning it the value there.

If no such value is found, an error is thrown. It only stores into variables that already exist, refusing to create new variables.

public SetValueExists ( string identifier, object value ) : void
identifier string variable name to attempt to store into
value object value to put into it
return void

StartCompileStopwatch() public method

public StartCompileStopwatch ( ) : void
return void

StatisticsDump() public method

public StatisticsDump ( bool doProfiling ) : string
doProfiling bool
return string

StopCompileStopwatch() public method

public StopCompileStopwatch ( ) : void
return void

SwitchToProgramContext() public method

public SwitchToProgramContext ( ) : IProgramContext
return IProgramContext

ToggleFlyByWire() public method

public ToggleFlyByWire ( string paramName, bool enabled ) : void
paramName string
enabled bool
return void

VariableIsRemovable() public method

public VariableIsRemovable ( Variable variable ) : bool
variable Variable
return bool

YieldProgram() public method

Call when you want to suspend execution of the Opcodes until some future condition becomes true. The CPU will call yieldTracker.Begin() right away, and then after that call yieldTracker.IsFinished() again and again until it returns true. Until IsFinished() returns true, the CPU will not advance any further into the program in its current "mode". Note that the CPU will track "trigger" and "mainline" code separately for this purpose. Waiting in mainline code will still allow triggers to run.
public YieldProgram ( YieldFinishedDetector yieldTracker ) : void
yieldTracker YieldFinishedDetector
return void