docs: function DevAdapter (controller) {
      
      // Define or LEX/Bison grammar to handle device packet
      var grammar = {
      "lex": {
          "rules" : [ ["\\s+" , "/* skip whitespace */"]
              // Lex rules==> smallest token after big/generic ones ex: 'b,'/'b', [A,C]/[a-Z], etc ...
              ,['help\\b'             , "return 'HELP';"]
              ,['quit\\b'             , "return 'QUIT';"]
              ,['ctrl\\b'             , "return 'CTRL';"]
              ,['back\\b'             , "return 'BACK';"]
              
              ,['evt\\b'              , "return 'EVTS';"]
              ,['start\\b'            , "return 'STAR';"]
              ,['on\\b'               , "return 'STAR';"]
              ,['stop\\b'             , "return 'STOP';"]
              ,['off\\b'              , "return 'STOP';"]
              
              ,['dev\\b'              , "return 'DEV';"]
              ,['list\\b'             , "return 'LIS';"]
              ,['login\\b'            , "return 'LOG';" ]
              ,['logout\\b'           , "return 'OUT';" ]
              ,['track\\b'            , "return 'TRK';" ]
              ,['info\\b'             , "return 'INF';" ]
              ,['track\\b'            , "return 'TRK';" ]
              
              ,['snd\\b'              , "return 'SEND';"]
              ,['all\\b'              , "return 'ALL';" ]
  
              ,['db\\b'               , "return 'BASE';"]
              ,['create\\b'           , "return 'CREA';"]
              ,['remove\\b'           , "return 'DROP';"]
              ,['search\\b'           , "return 'SEAR';"]
              ,['show\\b'             , "return 'SEAR';"]
              ,['init\\b'             , "return 'INIT';"]
  
              ,['[\',\"]'             , "/* ignored */" ]
              ,['[^ ]+\\b'            , "return 'TXT';" ]
              ,['\\n'                 , "return 'EOL';" ]
              ,[';'                   , "return 'EOL';" ]
              ,['$'                   , "return 'EOL';" ]
          ]
      },  // end Lex rules
      
      "bnf": { // WARNING: only one space in between TOKEN ex: "STOP EOF"
          'data': [["EOL"        ,"this.cmd='EMPTY'; return (this);"]
              ,["QUIT EOL"   ,"this.cmd='QUIT'   ; return (this);"]
              ,["HELP EOL"   ,"this.cmd='HELP'   ; return (this);"]
              ,["CTRL EOL"   ,"this.cmd='CONTROL'; return (this);"]
              ,["BACK EOL"   ,"this.cmd='BACKEND'; return (this);"]
              ,["COMMD EOL"  ,"return (this);"]
  
              ,["DEV LIS EOL"  ,"this.cmd='DEVLIST' ; return (this);"]
              ,["DEV ALL EOL"  ,"this.cmd='DEVALL' ; return (this);"]
              ,["DEV LOG TXT EOL"   ,"this.cmd='DEVIN'  ; this.devid=$3; return (this);"]
              ,["DEV OUT TXT EOL"   ,"this.cmd='DEVOUT' ; this.devid=$3; return (this);"]
              ,["DEV OUT ALL EOL"   ,"this.cmd='DEVOUT' ; this.devid=0;  return (this);"]
              ,["DEV TRK TXT EOL"   ,"this.cmd='DEVTRCK'; this.devid=$3; return (this);"]
              ,["DEV TRK ALL EOL"   ,"this.cmd='DEVTRCK'; this.devid=0;  return (this);"]
              ,["DEV INF TXT EOL"   ,"this.cmd='DEVINFO'; this.devid=$3; return (this);"]
  
              ,["BASE INIT EOL"     ,"this.cmd='DBINIT' ;return (this);"]
              ,["BASE DROP TXT EOL" ,"this.cmd='DBDROP' ; this.devid=$3;return (this);"]
              ,["BASE SEAR TXT EOL" ,"this.cmd='DBSEAR' ; this.devid=$3; this.args=5; return (this);"]
              ,["BASE SEAR TXT TXT EOL" ,"this.cmd='DBSEAR' ; this.devid=$3; this.limit=parseInt($4); return (this);"]
              ,["BASE CREA TXT TXT TXT TXT TXT TXT TXT ARGS EOL","this.cmd='DBCREA' ; this.devid=$3; this.mmsi=$4; this.callsign=$5; this.cargo=$6; this.length=$7; this.width=$8; this.model=$9; return (this);"]
  
              ,["EVTS STAR EOL" ,"this.cmd='EVTSTART' ; return (this);"]
              ,["EVTS STOP EOL" ,"this.cmd='EVTSTOP'  ; return (this);"]
             ] 
          ,'COMMD':[
              ,["SEND TXT ALL ARGS"     , "this.cmd='SEND'; this.action=$2; this.devid=0;"]
              ,["SEND TXT TXT ARGS"     , "this.cmd='SEND'; this.action=$2; this.devid=$3;"]
              ,["SEND TXT ALL"          , "this.cmd='SEND'; this.action=$2; this.devid=0;"]
              ,["SEND TXT TXT"          , "this.cmd='SEND'; this.action=$2; this.devid=$3;"]
              ,["SEND HELP TXT"         , "this.cmd='SEND'; this.devid=$3; this.action='help';"]
          ]
          ,'ARGS':[
               ["TXT"                   , "this.args=[$1];"]
              ,["ARGS TXT"              , "this.args.push ($2);"]
          ]
      }};
  
      this.id        = controller.svc;
      this.uid       = "//" + controller.svcopts.adapter + "/" + controller.svc + ":" +  controller.svcopts.port;;
      this.control   = "tcpsock";
      this.info      = "Telnet";
      this.debug     = controller.svcopts.debug;  // inherit debug from controller
      this.Debug     (1,"uid=%s", this.uid);
      this.controller= controller;  // keep a link to device controller and TCP socket
      this.parser    = new Jison(grammar);
      this.request   = 0; // job request number for gateway queue
      try {
          this.prompt= controller.gateway.opts.name +"> ";
      } catch (err) {
          this.prompt= "GatewayTracker> ";
      }
  }