Ah, the good old Hayes AT command set.
I've typically had the luxury of C, there are a couple of ways of doing this sort of thing, they are easier to read in C, but can be implemented in ASM.
RX ISR to FIFO
===========
First thing is get your receiver interrupt pushing the received data to a FIFO (circular software buffer), otherwise you may drop incoming bytes. In the modem world you have plenty of time to respond to a string, but you have to catch every byte. Have a look at your modems instruction book and see what the longest response string is, you will probably have started moving from your fifo to a buffer before you get to the end of the message, but what if you are busy elsewhere when the response comes in?
END OF STRING
=============
Now your main/match task will use your getbyte routine to poll the FIFO and build up a string for matching. When you get to the <CR> or <CR><LF> pair you can then attempt to match.
For AT modems I usually treat CR and LF as the same character and throw away the spares, this comes from my earlier life when I was working between Apples, Acorns and PC's, they each had different usage of CR, CR/LF and LF. Very painful. Of course driving a VT100, CR and LF are significant.
MATCHING
========
When you have your received string you then try to match against every string, until you have a match, that is do a string comp where you walk along the buffer and the string to match, aborting on first miss match. Each match string has a function pointer associated with it, or an enuerated value to index into your jump table.
TABLE OF STRINGS
===============
Having the inline hard coded testing is a pain to add, if you can declare strings you will find life easier, especially adding strings or changing.
Another method is to have multiple match pointers, each points to the start of your target strings. As you pop a byte from the buffer, if any of the strings match, you advance their pointer until you reach the end of the string.
e.g.
Target strings
OK
NO DIAL
NO SERVICE
t1ptr = (address of OK)
t2ptr = (address of NO DIAL)
t3ptr = (address of NO SERVICE)
when you get your first byte from the buffer, say an N you call a compare on each string, the OK fails to match, but the other two match first character, therefore advance t2ptr and t3ptr, you can probably see what's happening here... at the 4th character you can dismiss one of the two, but you must carry on to make sure the third string matches. Here you have a match pointer per string, and don't need to buffer the incoming string.
TREES
======
Now you implied you may have even more messages to deal with than the AT responses, handling SMS message content too. If you find you are having trouble managing a large number of strings you may want to build a tree structure for matching. Also you may want to consider a state machine whereby only certain message responses are legal in each context. I would not like to build a tree by hand. We built a preprocessor for a project so we could define values, very much like a #define. It built the tree for us.
TOKENS
=======
Your initial post implied you were going to sum your incoming bytes to make a token. Is this right?
errVal = asc('E')+asc('R')+asc('R')+asc('O')+asc('R') etc?
This can be dangerous as ERROR and EQSOT will evaluate to the same value. Even an XOR check sum would not help. I hear CRC can do this sort of uniqueness but is not fast to perform either. Sorry, character by character matching is more reliable and less prone to programming error.
WORD EXTRACTION or PARSING
==========================
If you are trying to pull a word out of a message you need to know how words are delimeted, and make sure that your word is properly formed. If I was looking for "BE" I would match it in "BETWEEN" and "AMBER" if I didn't look for space characters. I won't go into parsing here and now (as it's lunch time and I've waffled too much) but Parsing is the keyword you're looking for.