Esempio n. 1
0
  private BitSet getParamUsage(PreprocessorMacro macro) {
    final BitSet result = new BitSet();
    final TokenList replacement = macro.getTokens(fDefinitionParser, fLexOptions, this);

    Token l = null;
    Token n;
    for (Token t = replacement.first(); t != null; l = t, t = n) {
      n = (Token) t.getNext();
      switch (t.getType()) {
        case ObjCPreprocessor.tMACRO_PARAMETER:
          int idx = 2 * ((TokenParameterReference) t).getIndex();
          if (!isKind(n, IToken.tPOUNDPOUND)) {
            idx++;
          }
          result.set(idx);
          break;

        case IToken.tPOUND:
          if (isKind(n, ObjCPreprocessor.tMACRO_PARAMETER)) {
            idx = ((TokenParameterReference) n).getIndex();
            result.set(2 * idx);
            t = n;
            n = (Token) n.getNext();
          }
          break;

        case IToken.tPOUNDPOUND:
          if (isKind(n, ObjCPreprocessor.tMACRO_PARAMETER)) {
            idx = ((TokenParameterReference) n).getIndex();
            // gcc-extension
            if (isKind(l, IToken.tCOMMA)
                && macro.hasVarArgs() != FunctionStyleMacro.NO_VAARGS
                && idx == macro.getParameterPlaceholderList().length - 1
                && !isKind(n.getNext(), IToken.tPOUNDPOUND)) {
              result.set(2 * idx + 1);
            } else {
              result.set(2 * idx);
            }
            t = n;
            n = (Token) n.getNext();
          }
          break;
      }
    }
    return result;
  }
Esempio n. 2
0
  private void replaceArgs(
      PreprocessorMacro macro, TokenList[] args, TokenList[] expandedArgs, TokenList result) {
    TokenList replacement = clone(macro.getTokens(fDefinitionParser, fLexOptions, this));

    Token l = null;
    Token n;
    Token pasteArg1 = null;
    for (Token t = replacement.first(); t != null; l = t, t = n) {
      n = (Token) t.getNext();

      switch (t.getType()) {
        case ObjCPreprocessor.tMACRO_PARAMETER:
          int idx = ((TokenParameterReference) t).getIndex();
          if (idx < args.length) { // be defensive
            addSpacemarker(l, t, result); // start argument
            // replacement
            if (isKind(n, IToken.tPOUNDPOUND)) {
              TokenList arg = clone(args[idx]);
              pasteArg1 = arg.last();
              if (pasteArg1 != null) {
                result.appendAllButLast(arg);
                addSpacemarker(result.last(), pasteArg1, result); // start
                // token
                // paste
              }
            } else {
              TokenList arg = clone(expandedArgs[idx]);
              result.appendAll(arg);
              addSpacemarker(t, n, result); // end argument
              // replacement
            }
          }
          break;

        case IToken.tPOUND:
          addSpacemarker(l, t, result); // start stringify
          StringBuilder buf = new StringBuilder();
          buf.append('"');
          if (isKind(n, ObjCPreprocessor.tMACRO_PARAMETER)) {
            idx = ((TokenParameterReference) n).getIndex();
            if (idx < args.length) { // be defensive
              stringify(args[idx], buf);
            }
            t = n;
            n = (Token) n.getNext();
          }
          buf.append('"');
          final int length = buf.length();
          final char[] image = new char[length];
          buf.getChars(0, length, image, 0);

          Token generated = new TokenWithImage(IToken.tSTRING, null, 0, 0, image);
          if (isKind(n, IToken.tPOUNDPOUND)) { // start token paste,
            // same as start
            // stringify
            pasteArg1 = generated;
          } else {
            result.append(generated);
            addSpacemarker(t, n, result); // end stringify
          }
          break;

        case IToken.tPOUNDPOUND:
          Token pasteArg2 = null;
          TokenList rest = null;
          if (n != null) {
            if (n.getType() == ObjCPreprocessor.tMACRO_PARAMETER) {
              TokenList arg;
              idx = ((TokenParameterReference) n).getIndex();
              if (idx < args.length) { // be defensive
                arg = clone(args[idx]);
                pasteArg2 = arg.first();
                if (pasteArg2 != null && arg.first() != arg.last()) {
                  rest = arg;
                  rest.removeFirst();
                }
              }
            } else {
              idx = -1;
              pasteArg2 = n;
            }

            t = n;
            n = (Token) n.getNext();
            final boolean pasteNext = isKind(n, IToken.tPOUNDPOUND);

            generated = tokenpaste(pasteArg1, pasteArg2, macro);
            pasteArg1 = null;

            if (generated != null) {
              if (pasteNext && rest == null) {
                pasteArg1 = generated; // no need to mark
                // spaces, done ahead
              } else {
                result.append(generated);
                addSpacemarker(pasteArg2, rest == null ? n : rest.first(), result); // end
                // token
                // paste
              }
            }
            if (rest != null) {
              if (pasteNext) {
                pasteArg1 = rest.last();
                if (pasteArg1 != null) {
                  result.appendAllButLast(rest);
                  addSpacemarker(result.last(), pasteArg1, result); // start
                  // token
                  // paste
                }
              } else {
                result.appendAll(rest);
                if (idx >= 0) {
                  addSpacemarker(t, n, result); // end
                  // argument
                  // replacement
                }
              }
            }
          }
          break;

        case IToken.tCOMMA:
          if (isKind(n, IToken.tPOUNDPOUND)) {
            final Token nn = (Token) n.getNext();
            if (isKind(nn, ObjCPreprocessor.tMACRO_PARAMETER)) {
              idx = ((TokenParameterReference) nn).getIndex();

              // check for gcc-extension preventing the paste
              // operation
              if (idx == args.length - 1
                  && macro.hasVarArgs() != FunctionStyleMacro.NO_VAARGS
                  && !isKind(nn.getNext(), IToken.tPOUNDPOUND)) {
                final Token nnn = (Token) nn.getNext();
                TokenList arg = clone(expandedArgs[idx]);
                if (arg.isEmpty()) {
                  addSpacemarker(l, t, result);
                  addSpacemarker(nn, nnn, result);
                } else {
                  result.append(t);
                  addSpacemarker(t, n, result);
                  result.appendAll(arg);
                  addSpacemarker(nn, nnn, result);
                }
                t = nn;
                n = nnn;
                break;
              }
            }

            addSpacemarker(l, t, result);
            pasteArg1 = t;
          } else {
            result.append(t);
          }
          break;

        default:
          if (isKind(n, IToken.tPOUNDPOUND)) {
            addSpacemarker(l, t, result); // start token paste
            pasteArg1 = t;
          } else {
            result.append(t);
          }
          break;
      }
    }
  }