gmSCCodePatternClass
The CodePattern Service Class
Section titled “The CodePattern Service Class”The service class CodePattern contains methods to provide a better notation for doing tests like the following within the tool code and to provide a facility for doing tests like this in gmSL.
if(codptr[icode ] == OPC_LDA && codptr[icode+5 ] == OPC_LSB && codptr[icode+6 ] == LSB_List && codptr[icode+7 ] == OPC_MEM && codptr[icode+9 ] == OPC_LEV && codptr[icode+11] == OPC_LDA && codptr[icode+16] == OPC_LSB && codptr[icode+17] == LSB_ListIndex && codptr[icode+18] == OPC_MEM && codptr[icode+20] == OPC_ARG && codptr[icode+22] == OPC_INX)The issue is that code like this requires that the user be very familiar with not just the operation codes, but also with how these codes are physically laid out in the code vector. That the user must know the opcodes is still a requirement. Higher level methods are provided but they do not always provide the needed level of detail and whether they actually remove the need to know the opcodes themselves is questionable. The need to know the layouts — i.e. the number of bytes associated with each opcode and the resultant offsets — can be removed by observing that there are two types of tests performed: (1) a test for the opcode itself only and (2) a test for the opcode and its associated subcode information. A match operation is needed that says “match the opcode and if OK move to the next opcode”. This match operation is performed by a new opcode OPC whose subcodes are the opcodes. This opcode is entered into the file opcodes.xml in the standard way.
<opcode id="OPC" opc="127" type="DoubleByte" role="none" subcodes="181" > <subcode id="NEW" value="0" /> <!-- Start new command --> <subcode id="LDA" value="1" /> <!-- Load a variable address --> ....In addition an opcode to control the overall match logic is needed. It is called OPO and has five subcodes.
<opcode id="OPO" opc="178" type="DoubleByte" role="none" subcodes="5" > <subcode id="EndList" value="0" /> <subcode id="Argument" value="1" /> <subcode id="Lvalue" value="2" /> <subcode id="FindMatch" value="3" /> <subcode id="Comment" value="4" /> </opcode>Given these additional opcodes it is now possible to write a static operation specification.
static UBYTE anaSetSelected[] = { OPC_OPC,OPC_LDA, OPC_LSB,LSB_List, OPC_OPC,OPC_MEM, OPC_OPC,OPC_LEV, OPC_OPC,OPC_LDA, OPC_LSB,LSB_ListIndex, OPC_OPC,OPC_MEM, OPC_OPC,OPC_ARG, OPC_OPC,OPC_INX, OPC_OPO,OPO_EndList };Methods in this class perform matches using these code pattern specifications and methods that read them using a simplified notation for use primarily by gmSL.
The method CodePattern_FindOpcode
Section titled “The method CodePattern_FindOpcode”Prototype
int CodePattern_FindOpcode(char* ident);The CodePattern_FindOpcode method finds an opcode given its identifier. It looks up the label for a particular opcode in the OPCODES information for the language. Its parameter is:
| Parameter | Description |
|---|---|
| ident | Contains the opcode identifier in null-terminated string form. |
If there is an opcode with the indicated identifier, then its opc value is returned. If no such opcode exists, then a minus one is returned.
The method CodePattern_FindSubcode
Section titled “The method CodePattern_FindSubcode”Prototype
int CodePattern_FindSubcode(int opcode,char* label);The CodePattern_FindSubcode method finds a subcode of a give opcode via the subcode label. Its parameters are:
| Parameter | Description |
|---|---|
| opcode | Contains the sequence number of the desired opcode. This was the opc attribute of opcode when it was defined. |
| label | Contains a null-terminated string specifying the label to be searched for. |
If found, the method returns the subcode value that was assigned. If not found, it returns a minus one.
The method CodePattern_Match
Section titled “The method CodePattern_Match”Prototype
int CodePattern_Match(UBYTE* pcode,int opadr,UBYTE* operation);The CodePattern_Match method checks if a sequence of operation codes in a code block match a code pattern. Its parameters are:
| Parameter | Description |
|---|---|
| pcode | Contains the code block being checked against the code pattern. |
| opadr | Specifies the offset of the start of the actual operation codes in the code block. |
| operation | contains the code pattern to be matched. |
If a match is made, then the method returns the offset of the first byte in the code block beyond the end of the match. If no match is made, the method returns zero.
The method CodePattern_Read
Section titled “The method CodePattern_Read”Prototype
int CodePattern_Read(char* source,UBYTE* operation);The CodePattern_Read method reads a simplified representation of a code pattern. Its parameters are:
| Parameter | Description |
|---|---|
| source | Contains the source representation of the code pattern in null-terminated form. |
| operation | receives the code pattern itself in operation code form. |
If all goes well, the method returns the length of the compiled code pattern; else it returns one of the following negative error codes:
| code | Meaning |
|---|---|
| -1 | An unrecognized opcode operation (OPO subcode) was encountered. |
| -2 | The subcode identifier associated with an opcode was not recognized. |
| -3 | The closing square bracket ending a bracketed identifier was missing. |
| -4 | A source code identifier was not found. |