/[svn]/linuxsampler/trunk/src/network/lscp.y
ViewVC logotype

Diff of /linuxsampler/trunk/src/network/lscp.y

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2525 by schoenebeck, Mon Feb 24 17:52:51 2014 UTC revision 2531 by schoenebeck, Wed Mar 5 00:02:21 2014 UTC
# Line 43  namespace LinuxSampler { Line 43  namespace LinuxSampler {
43  // to save us typing work in the rules action definitions  // to save us typing work in the rules action definitions
44  #define LSCPSERVER ((yyparse_param_t*) yyparse_param)->pServer  #define LSCPSERVER ((yyparse_param_t*) yyparse_param)->pServer
45  #define SESSION_PARAM ((yyparse_param_t*) yyparse_param)  #define SESSION_PARAM ((yyparse_param_t*) yyparse_param)
46  #define INCREMENT_LINE { SESSION_PARAM->iLine++; SESSION_PARAM->iColumn = 0; sParsed.clear(); }  #define INCREMENT_LINE { SESSION_PARAM->onNextLine(); sParsed.clear(); }
47    
48  // clears input buffer  // clears input buffer
49  void restart(yyparse_param_t* pparam, int& yychar);  void restart(yyparse_param_t* pparam, int& yychar);
# Line 1840  static std::set<String> yyExpectedSymbol Line 1840  static std::set<String> yyExpectedSymbol
1840   * because it would end up in an endless loop otherwise.   * because it would end up in an endless loop otherwise.
1841   *   *
1842   * This solution consumes a lot of memory, but unfortunately there is no other   * This solution consumes a lot of memory, but unfortunately there is no other
1843   * easy way to solve it. With our grammar and today's memory heap & memory stack   * easy way to solve it. With our grammar and today's memory heap size & memory
1844   * it should be fine though.   * stack size it should be fine though.
1845   */   */
1846  typedef std::set< std::vector<YYTYPE_INT16> > YYStackHistory;  typedef std::set< std::vector<YYTYPE_INT16> > YYStackHistory;
1847    
# Line 2009  namespace LinuxSampler { Line 2009  namespace LinuxSampler {
2009   * application will only have to show the results of the LSCP server's   * application will only have to show the results of the LSCP server's
2010   * evaluation to the user on the screen.   * evaluation to the user on the screen.
2011   *   *
2012     * @param line - the current command line to be evaluated by LSCP parser
2013     * @param param = reentrant parser session parameters
2014     * @param possibilities - whether all possibilities shall be shown
2015   * @returns LSCP shell response line to be returned to the client   * @returns LSCP shell response line to be returned to the client
2016   */   */
2017  String lscpParserProcessShellInteraction(String& line, yyparse_param_t* param) {  String lscpParserProcessShellInteraction(String& line, yyparse_param_t* param, bool possibilities) {
2018      // first, determine how many characters (starting from the left) of the      // first, determine how many characters (starting from the left) of the
2019      // given input line are already syntactically correct      // given input line are already syntactically correct
2020      std::vector<YYTYPE_INT16> stack;      std::vector<YYTYPE_INT16> stack;
# Line 2026  String lscpParserProcessShellInteraction Line 2029  String lscpParserProcessShellInteraction
2029          line.replace(0, nMin, l.substr(0, nMin));          line.replace(0, nMin, l.substr(0, nMin));
2030      }      }
2031    
2032        size_t cursorPos = line.size() + param->iCursorOffset;
2033        if (cursorPos < 0) cursorPos = 0;
2034    
2035      // generate an info string that will be sent to the LSCP shell for letting      // generate an info string that will be sent to the LSCP shell for letting
2036      // it know which part is correct, which one is wrong, where is the cursor, etc.      // it know which part is correct, which one is wrong, where is the cursor, etc.
2037      String result = line;      String result = line;
2038      result.insert(n <= result.length() ? n : result.length(), LSCP_SHK_GOOD_FRONT);      result.insert(n <= result.length() ? n : result.length(), LSCP_SHK_GOOD_FRONT);
2039        result.insert(cursorPos <= n ? cursorPos : cursorPos + String(LSCP_SHK_GOOD_FRONT).length(), LSCP_SHK_CURSOR);
2040      int code = (n > line.length()) ? LSCP_SHU_COMPLETE : (n < line.length()) ?      int code = (n > line.length()) ? LSCP_SHU_COMPLETE : (n < line.length()) ?
2041                 LSCP_SHU_SYNTAX_ERR : LSCP_SHU_INCOMPLETE;                 LSCP_SHU_SYNTAX_ERR : LSCP_SHU_INCOMPLETE;
2042      result = "SHU:" + ToString(code) + ":" + result + LSCP_SHK_CURSOR;      result = "SHU:" + ToString(code) + ":" + result;
2043      //if (n > line.length()) result += " [OK]";      //if (n > line.length()) result += " [OK]";
2044    
2045      // get a clean parser stack to the last valid parse position      // get a clean parser stack to the last valid parse position
# Line 2044  String lscpParserProcessShellInteraction Line 2051  String lscpParserProcessShellInteraction
2051      if (!l.empty()) yyValidCharacters(stack, l, param->bShellAutoCorrect);      if (!l.empty()) yyValidCharacters(stack, l, param->bShellAutoCorrect);
2052    
2053      // generate auto completion suggestion (based on the current parser stack)      // generate auto completion suggestion (based on the current parser stack)
2054      String sSuggestion = yyAutoComplete(stack);      std::vector<YYTYPE_INT16> stackCopy = stack; // make a copy, since yyAutoComplete() might alter the stack
2055        String sSuggestion = yyAutoComplete(stackCopy);
2056      if (!sSuggestion.empty()) result += LSCP_SHK_SUGGEST_BACK + sSuggestion;      if (!sSuggestion.empty()) result += LSCP_SHK_SUGGEST_BACK + sSuggestion;
2057    
2058        if (!possibilities) return result;
2059    
2060        // finally append all possible terminals and non-terminals according to
2061        // current parser state
2062        String notUsedHere;
2063        std::map<String,BisonSymbolInfo> expectedSymbols;
2064        walkAndFillExpectedSymbols(stack, expectedSymbols, notUsedHere);
2065        {
2066            // pretend to LSCP shell that the following terminal symbols were
2067            // non-terminal symbols (since they are not human visible for auto
2068            // completion on the shell's screen)
2069            std::set<String> specialNonTerminals;
2070            specialNonTerminals.insert("SP");
2071            specialNonTerminals.insert("CR");
2072            specialNonTerminals.insert("LF");
2073    
2074            String sPossibilities;
2075            int iNonTerminals = 0;
2076            int iTerminals    = 0;
2077            for (std::map<String,BisonSymbolInfo>::const_iterator it = expectedSymbols.begin();
2078                 it != expectedSymbols.end(); ++it)
2079            {
2080                if (!sPossibilities.empty()) sPossibilities += " | ";
2081                if (it->second.isTerminalSymbol && !specialNonTerminals.count(it->first)) {
2082                    sPossibilities += it->first;
2083                    iTerminals++;
2084                } else {
2085                    sPossibilities += "<" + it->first + ">";
2086                    iNonTerminals++;
2087                }
2088            }
2089            if (!sPossibilities.empty() && (iNonTerminals || iTerminals > 1)) {
2090                result += LSCP_SHK_POSSIBILITIES_BACK + sPossibilities;
2091            }
2092        }
2093    
2094  #if DEBUG_SHELL_INTERACTION  #if DEBUG_SHELL_INTERACTION
2095      printf("%s\n", result.c_str());      printf("%s\n", result.c_str());
2096  #endif  #endif

Legend:
Removed from v.2525  
changed lines
  Added in v.2531

  ViewVC Help
Powered by ViewVC