you can do this by having oof parse words from the input stream until it parses foo, and all the facilities for doing that are included in the ansi standard (i.e., it doesn't require knowledge of theoretically private implementation details of a given forth). there aren't any standard words that work this way, although, as you're probably aware, \ " .( ( char [char] c" s" and ." do consume data from the input stream in various ways (but without parsing it into words), and in particular ' ['] create value variable constant marker parse-name to defer is and postpone all read a single word from the input and do various things with it
i'm no forth expert but i think you can define your desired oof as follows in ans forth:
: roof begin parse-name \ read oof
2dup s" foo" compare 0= if 2drop exit then spoof again ;
: oof immediate goof roof proof ;
what this does is determined by pre-existing definitions for goof, spoof, and proof. spoof somehow accumulates a word, while goof and proof are invoked at the beginning and end of the string of words. the simplest interesting thing to do is to concatenate them in a buffer and type them out, which can be accomplished by providing the following definitions before compiling the above: create boof 256 allot 0 value poof \ buffer and pointer for oof
: proof boof poof type ; : goof 0 to poof ; \ print oof, gone oof
: spoof >r poof boof + r@ move r> poof + to poof ; \ string put for poof
if you defer goof, spoof, and proof, you can change what they do without recompiling oof and roofi can't swear that this is ansi-compliant forth but i did test it in gforth and pfe. i also tried testing it in yforth and jonesforth but couldn't get them to run on this amd64 linux
the one debatable thing here is that you said 'symbols', but spoof's arguments are just a string pointer and a length, probably in some kind of input buffer. forth doesn't natively have symbols in the lisp sense, but it does have something very similar, which is a dictionary of words. spoof can look up a word in the dictionary in the same way ' or ['] would, by using the word find†, which returns a pointer to the word's dictionary entry (a so-called 'execution token')
this may sound suspiciously like symbol interning in lisp, and if the naming of ' in forth isn't inspired by the lisp readmacro of the same name, it's at least a damned suspicious coincidence. but the semantics are different from interning in an important way, which is why i didn't use find in my definition of roof above: if the word you're searching for hasn't been defined, find doesn't add it to the dictionary. for dup, rot, and swap, you'd be fine, but if you stuck a bar or a quux in there, find would return 0 (and the original string). also, in forth, you can have more than one word with the same spelling, and find will only find the latest one that's still in scope, which is a different behavior from lisp symbols
if you want the lisp symbol behavior, you'd have to define your own obarray and intern, which is not too hard
______
† the standard word find wants a counted string, and that's enough hassle that many implementations like gforth provide a find-name which takes a string in the format provided by parse-name instead, and define find in terms of find-name. but find-name isn't in the ans standard, and you can define it in terms of find if you have to