iiStrFind bb#,nn,c [D>=28]
Match a string in RAM to a table in NVEM. This is subtly different to iiStrFind2, which uses a different table format.
Consider an Xwire receive data block to be nn bytes of RAM starting at address bb. This instruction seeks to match the data in the block with one or more “canned” strings stored in NVEM. Its primary use is for decoding information that has come in via an Xwire peripheral.
If argument c is zero, the instruction treats upper and lower case letters as equivalent. If c is non-zero, the case of the RAM string must match exactly the string stored in NVEM.
The data in NVEM must be stored in a very specific “NULL terminated” format. This is best illustrated by an example. Lets say we want to detect which fruit has been requested via an Internet interface and transferred into an Xwire receive data block.
1. NVEM: Message list
First you construct a list of all possible receive strings in NVEM. Each string must be terminated with a 0 byte. The 0 is not part of the string, it merely signals the end of the string (C-style NULL terminated strings).
strOrange: NV0Byte "Orange",13,0 strApple: NV0Byte "Apple",13,0 strBanana: NV0Byte "Banana",13,0 strLemon: NV0Byte "Lemon",13,0 strPear: NV0Byte "Pear",13,0 strGrape: NV0Byte "Grape",13,0 ; Terminator _________________^
2. NVEM: Pointer table
Next you construct a table, in NVEM, of pointers to the individual strings. This must be terminated in two 255 bytes. The 255s tell iiStrFind that it has come to the end of the table.
FruitNames: NV0Ptr strOrange ;Entry #1
NV0Ptr strLemon ;Entry #2
NV0Ptr strApple ;Entry #3
NV0Ptr strPear ;Entry #4
NV0Ptr strBanana ;Entry #5
NV0Ptr strGrape ;Entry #6
NV0Byte 255,255 ;<<<<< Essential!!!
You will notice that the order of entries is different to the order of the strings themselves. They can be in any order you like. You can have several such tables, with different ordering. You can even use different sub-sets of strings at
3. Code: Wait for a message string
Before trying to extract or recognize a string, you must know that a string has actually been received. How you do this will depend on the particular source of the data that is being stored in RAM. We cannot therefore provide such detail here. (See ComRx_StrFind to see how it’s done for serial data). Here we’ll just have example code for defining the Rx data block.:
XWRxBlock defBYTE 30 XWRxBlkLen EQU 30
4. Code: Find a string match.
This is where we use the actual iiStrFind instruction. First we have to make sure the NVEM access is correctly set up.
NVSetPtr FruitNames
NVSetPage 0 ;0 is the default, so playing very safe!
LoadI 0 ;Start the search at the start of the buffer
iiStrFind XWRxBlock,XWRxBlkfLen,0
5. Code: Evaluate the result.
The iiStrFind returns its result in X, as follows:
- If a match is found, the
X-register contains the number of the entry in the pointer table, counting from 1. Thus, if in this case the received string was"Apple",13,Xwould contain 3. - If a match is not found,
Xwill contain 0 (which makesBranchinstruction very appropriate).
If a match is found, the index register I is incremented to point to the first character in RAM after the string (auto-index).
Branch
Target NoMatch
Target RxOrange
Target RxLemon
Target RxApple
Target RxPear
Target RxBanana
Target RxGrape
RxOrange: ;Do the orange thing ....
RxLemon: ;Do the lemon thing ....
RxApple: ;Do the apple thing ....
RxPear: ;Do the pear thing ....
RxBanana: ;Do the banana thing ....
RxGrape: ;Do the grape thing ....
You would place your own code to respond to each of the strings atRxOrange,RxLemon, etc.
Quite likely you would then go back to waiting for the next incoming message.
Notes/reminders:
- The instruction only moves
Ipast the characters of any string it matches. - The string must start at the position initially pointed to by
I. - The 3rd instruction argument controls case sensitivity
- Each string in NVEM must end in a 0 (NULL) byte.
- The table of pointers must end in two 255 bytes.
- The record length and record number pointers are not involved in this instruction. Only the page and pointer matter.
- The
ComRx_StrFindinstruction has very similar behaviour, only it works on data received via the serial port.