VirtualBox

Changeset 76506 in vbox


Ignore:
Timestamp:
Dec 30, 2018 3:41:21 AM (6 years ago)
Author:
vboxsync
Message:

scm: Header guard massaging for adding #pragma once. bugref:9344

Location:
trunk/src/bldprogs
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/bldprogs/VBoxTpG.cpp

    r76474 r76506  
    969969                    "#ifndef %s\n"
    970970                    "#define %s\n"
     971                    "#ifndef RT_WITHOUT_PRAGMA_ONCE\n"
     972                    "# pragma once\n"
     973                    "#endif\n"
    971974                    "\n"
    972975                    "#include <VBox/VBoxTpG.h>\n"
  • trunk/src/bldprogs/scm.cpp

    r76476 r76506  
    7575    SCMOPT_FIX_FLOWER_BOX_MARKERS,
    7676    SCMOPT_NO_FIX_FLOWER_BOX_MARKERS,
     77    SCMOPT_FIX_HEADER_GUARDS,
     78    SCMOPT_NO_FIX_HEADER_GUARDS,
    7779    SCMOPT_FIX_TODOS,
    7880    SCMOPT_NO_FIX_TODOS,
     
    175177    /* .fFixFlowerBoxMarkers = */                   true,
    176178    /* .cMinBlankLinesBeforeFlowerBoxMakers = */    2,
     179    /* .fFixHeaderGuards = */                       false, /** @todo fFixHeaderGuards = true */
    177180    /* .fFixTodos = */                              true,
    178181    /* .fFixErrH = */                               true,
     
    215218    { "--fix-flower-box-markers",           SCMOPT_FIX_FLOWER_BOX_MARKERS,          RTGETOPT_REQ_NOTHING },
    216219    { "--no-fix-flower-box-markers",        SCMOPT_NO_FIX_FLOWER_BOX_MARKERS,       RTGETOPT_REQ_NOTHING },
     220    { "--fix-header-guards",                SCMOPT_FIX_HEADER_GUARDS,               RTGETOPT_REQ_NOTHING },
     221    { "--no-fix-header-guards",             SCMOPT_NO_FIX_HEADER_GUARDS,            RTGETOPT_REQ_NOTHING },
    217222    { "--fix-todos",                        SCMOPT_FIX_TODOS,                       RTGETOPT_REQ_NOTHING },
    218223    { "--no-fix-todos",                     SCMOPT_NO_FIX_TODOS,                    RTGETOPT_REQ_NOTHING },
     
    289294SCM_REWRITER_CFG(g_Makefile_kmk,                    "makefile-kmk",                 rewrite_Makefile_kmk);
    290295SCM_REWRITER_CFG(g_FixFlowerBoxMarkers,             "fix-flower-boxes",             rewrite_FixFlowerBoxMarkers);
     296SCM_REWRITER_CFG(g_FixHeaderGuards,                 "fix-header-guard",             rewrite_FixHeaderGuards);
    291297SCM_REWRITER_CFG(g_Fix_C_and_CPP_Todos,             "fix-c-todos",                  rewrite_Fix_C_and_CPP_Todos);
    292298SCM_REWRITER_CFG(g_Fix_Err_H,                       "fix-err-h",                    rewrite_Fix_Err_H);
     
    318324    &g_Makefile_kmk,
    319325    &g_FixFlowerBoxMarkers,
     326    &g_FixHeaderGuards,
    320327    &g_Fix_C_and_CPP_Todos,
    321328    &g_Fix_Err_H,
     
    380387    &g_SvnSyncProcess,
    381388    &g_Copyright_CstyleComment,
     389    /// @todo &g_FixFlowerBoxMarkers,
     390    &g_FixHeaderGuards,
    382391    &g_C_and_CPP
    383392};
     
    10041013        case SCMOPT_NO_FIX_FLOWER_BOX_MARKERS:
    10051014            pSettings->fFixFlowerBoxMarkers = false;
     1015            return VINF_SUCCESS;
     1016
     1017        case SCMOPT_FIX_HEADER_GUARDS:
     1018            pSettings->fFixHeaderGuards = true;
     1019            return VINF_SUCCESS;
     1020        case SCMOPT_NO_FIX_HEADER_GUARDS:
     1021            pSettings->fFixHeaderGuards = false;
    10061022            return VINF_SUCCESS;
    10071023
     
    26742690            case SCMOPT_MIN_BLANK_LINES_BEFORE_FLOWER_BOX_MARKERS: RTPrintf("      Default: %u\n", g_Defaults.cMinBlankLinesBeforeFlowerBoxMakers); break;
    26752691
     2692            case SCMOPT_FIX_HEADER_GUARDS:
     2693                RTPrintf("      Fix header guards and #pragma once.  Default: %RTbool\n", g_Defaults.fFixHeaderGuards);
     2694                break;
    26762695            case SCMOPT_FIX_TODOS:
    26772696                RTPrintf("      Fix @todo statements so doxygen sees them.  Default: %RTbool\n", g_Defaults.fFixTodos);
  • trunk/src/bldprogs/scm.h

    r76451 r76506  
    187187 * @sa      vbcppIsCIdentifierChar
    188188 */
    189 DECLINLINE(bool) scmIsCIdentifierChar(char ch)
     189DECLINLINE(bool) ScmIsCIdentifierChar(char ch)
    190190{
    191191    return RT_C_IS_ALNUM(ch)
     
    260260FNSCMREWRITER rewrite_Fix_C_and_CPP_Todos;
    261261FNSCMREWRITER rewrite_Fix_Err_H;
     262FNSCMREWRITER rewrite_FixHeaderGuards;
    262263FNSCMREWRITER rewrite_C_and_CPP;
    263264
     
    330331    /** The minimum number of blank lines we want before flowerbox markers. */
    331332    uint8_t         cMinBlankLinesBeforeFlowerBoxMakers;
     333
     334    /** Whether to fix C/C++ header guards and \#pragma once directives. */
     335    bool            fFixHeaderGuards;
    332336
    333337    /** Whether to fix C/C++ todos. */
  • trunk/src/bldprogs/scmrw.cpp

    r76478 r76506  
    24062406
    24072407
    2408 
    24092408/**
    24102409 * Tries to parse a C/C++ preprocessor include directive.
     
    24692468                        return chFirst == '"' ? kScmIncludeDir_Quoted : kScmIncludeDir_Bracketed;
    24702469                    }
    2471                     ScmError(pState,  VERR_PARSE_ERROR, "Unbalanced #include filename %s: %.*s\n",
     2470                    ScmError(pState, VERR_PARSE_ERROR, "Unbalanced #include filename %s: %.*s\n",
    24722471                             chFirst == '"' ? "quotes" : "brackets" , cchLine, pchLine);
    24732472                }
     
    24772476                    size_t cchFilename = 1;
    24782477                    while (   cchFilename < cchLine
    2479                            && scmIsCIdentifierChar(pchLine[cchFilename]))
     2478                           && ScmIsCIdentifierChar(pchLine[cchFilename]))
    24802479                        cchFilename++;
    24812480                    if (ppchFilename)
     
    24862485                }
    24872486                else
    2488                     ScmError(pState,  VERR_PARSE_ERROR, "Malformed #include filename part: %.*s\n", cchLine, pchLine);
     2487                    ScmError(pState, VERR_PARSE_ERROR, "Malformed #include filename part: %.*s\n", cchLine, pchLine);
    24892488            }
    24902489            else
    2491                 ScmError(pState,  VERR_PARSE_ERROR, "Missing #include filename!\n");
     2490                ScmError(pState, VERR_PARSE_ERROR, "Missing #include filename!\n");
    24922491        }
    24932492    }
     
    26592658                if (    pchHit[4] == '_'
    26602659                    && (   pchHit == pchLine
    2661                         || !scmIsCIdentifierChar(pchHit[-1]))
     2660                        || !ScmIsCIdentifierChar(pchHit[-1]))
    26622661                    && (   (pchHit[1] == 'E' && pchHit[2] == 'R' && pchHit[3] == 'R')
    26632662                        || (pchHit[1] == 'W' && pchHit[2] == 'R' && pchHit[3] == 'N')
     
    26652664                {
    26662665                    size_t cchIdentifier = 5;
    2667                     while (cchIdentifier < cchLeftHit && scmIsCIdentifierChar(pchHit[cchIdentifier]))
     2666                    while (cchIdentifier < cchLeftHit && ScmIsCIdentifierChar(pchHit[cchIdentifier]))
    26682667                        cchIdentifier++;
    26692668                    ScmVerbose(pState, 4, "--- status code at %u col %zu: %.*s\n",
     
    27512750}
    27522751
     2752typedef struct
     2753{
     2754    const char     *pch;
     2755    uint8_t         cch;
     2756    uint8_t         cchSpaces;          /**< Number of expected spaces before the word. */
     2757    bool            fSpacesBefore : 1;  /**< Whether there may be spaces or tabs before the word. */
     2758    bool            fIdentifier   : 1;  /**< Whether we're to expect a C/C++ identifier rather than pch/cch. */
     2759} SCMMATCHWORD;
     2760
     2761
     2762int ScmMatchWords(const char *pchLine, size_t cchLine, SCMMATCHWORD const *paWords, size_t cWords,
     2763                  size_t *poffNext, PRTSTRTUPLE paIdentifiers, PRTERRINFO pErrInfo)
     2764{
     2765    int rc = VINF_SUCCESS;
     2766
     2767    size_t offLine = 0;
     2768    for (size_t i = 0; i < cWords; i++)
     2769    {
     2770        SCMMATCHWORD const *pWord = &paWords[i];
     2771
     2772        /*
     2773         * Deal with spaces preceeding the word first:
     2774         */
     2775        if (pWord->fSpacesBefore)
     2776        {
     2777            size_t cchSpaces = 0;
     2778            size_t cchTabs   = 0;
     2779            while (offLine < cchLine)
     2780            {
     2781                const char ch = pchLine[offLine];
     2782                if (ch == ' ')
     2783                    cchSpaces++;
     2784                else if (ch == '\t')
     2785                    cchTabs++;
     2786                else
     2787                    break;
     2788                offLine++;
     2789            }
     2790
     2791            if (cchSpaces == pWord->cchSpaces && cchTabs == 0)
     2792            { /* likely */ }
     2793            else if (cchSpaces == 0 && cchTabs == 0)
     2794                return RTErrInfoSetF(pErrInfo, VERR_PARSE_ERROR, "expected space at offset %u", offLine);
     2795            else
     2796                rc = VWRN_TRAILING_SPACES;
     2797        }
     2798        else
     2799            Assert(pWord->cchSpaces == 0);
     2800
     2801        /*
     2802         * C/C++ identifier?
     2803         */
     2804        if (pWord->fIdentifier)
     2805        {
     2806            if (offLine >= cchLine)
     2807                return RTErrInfoSetF(pErrInfo, VERR_END_OF_STRING,
     2808                                     "expected '%.*s' (C/C++ identifier) at offset %u, not end of string",
     2809                                     pWord->cch, pWord->pch, offLine);
     2810            if (!ScmIsCIdentifierLeadChar(pchLine[offLine]))
     2811                return RTErrInfoSetF(pErrInfo, VERR_MISMATCH, "expected '%.*s' (C/C++ identifier) at offset %u",
     2812                                     pWord->cch, pWord->pch, offLine);
     2813            size_t const offStart = offLine++;
     2814            while (offLine < cchLine && ScmIsCIdentifierChar(pchLine[offLine]))
     2815                offLine++;
     2816            if (paIdentifiers)
     2817            {
     2818                paIdentifiers->cch = offLine - offStart;
     2819                paIdentifiers->psz = &pchLine[offStart];
     2820                paIdentifiers++;
     2821            }
     2822        }
     2823        /*
     2824         * Match the exact word.
     2825         */
     2826        else if (   pWord->cch == 0
     2827                 || (   pWord->cch <= cchLine - offLine
     2828                     && !memcmp(pWord->pch, &pchLine[offLine], pWord->cch)))
     2829            offLine += pWord->cch;
     2830        else
     2831            return RTErrInfoSetF(pErrInfo, VERR_MISMATCH, "expected '%.*s' at offset %u", pWord->cch, pWord->pch, offLine);
     2832    }
     2833
     2834    /*
     2835     * Check for trailing characters/whatnot.
     2836     */
     2837    if (poffNext)
     2838        *poffNext = offLine;
     2839    else if (offLine != cchLine)
     2840        rc = RTErrInfoSetF(pErrInfo, VERR_TRAILING_CHARS, "unexpected trailing characters at offset %u", offLine);
     2841    return rc;
     2842}
     2843
     2844
     2845/**
     2846 * Fix header file include guards and \#pragma once.
     2847 *
     2848 * @returns true if modifications were made, false if not.
     2849 * @param   pIn                 The input stream.
     2850 * @param   pOut                The output stream.
     2851 * @param   pSettings           The settings.
     2852 */
     2853bool rewrite_FixHeaderGuards(PSCMRWSTATE pState, PSCMSTREAM pIn, PSCMSTREAM pOut, PCSCMSETTINGSBASE pSettings)
     2854{
     2855    if (!pSettings->fFixHeaderGuards)
     2856        return false;
     2857
     2858    int rc;
     2859    bool fRet = false;
     2860    RTERRINFOSTATIC ErrInfo;
     2861
     2862    /*
     2863     * First part looks for the #ifndef xxxx paired with #define xxxx.
     2864     *
     2865     * We blindly assume the first preprocessor directive in the file is the guard
     2866     * and will be upset if this isn't the case.
     2867     */
     2868    uint32_t    cBlankLines = 0;
     2869    SCMEOL      enmEol;
     2870    size_t      cchLine;
     2871    const char *pchLine;
     2872    for (;;)
     2873    {
     2874        pchLine = ScmStreamGetLine(pIn, &cchLine, &enmEol);
     2875        if (pchLine == NULL)
     2876            return ScmError(pState, VERR_PARSE_ERROR, "Did not find any include guards!\n");
     2877        if (cchLine >= 2)
     2878        {
     2879            const char *pchHash = (const char *)memchr(pchLine, '#', cchLine);
     2880            if (    pchHash
     2881                && isSpanOfBlanks(pchLine, pchHash - pchLine))
     2882            {
     2883                /* #ifndef xxxx */
     2884                static const SCMMATCHWORD s_aIfndefGuard[] =
     2885                {
     2886                    { RT_STR_TUPLE("#"),                0, true, false },
     2887                    { RT_STR_TUPLE("ifndef"),           0, true, false },
     2888                    { RT_STR_TUPLE("IDENTIFIER"),       1, true, true },
     2889                    { RT_STR_TUPLE(""),                 0, true, false },
     2890                };
     2891                RTSTRTUPLE Guard;
     2892                rc = ScmMatchWords(pchLine, cchLine, s_aIfndefGuard, RT_ELEMENTS(s_aIfndefGuard),
     2893                                   NULL /*poffNext*/, &Guard, RTErrInfoInitStatic(&ErrInfo));
     2894                if (RT_FAILURE(rc))
     2895                    return ScmError(pState, rc, "%u: Expected first preprocessor directive to be '#ifndef xxxx'. %s (%.*s)\n",
     2896                                    ScmStreamTellLine(pIn) - 1, ErrInfo.Core.pszMsg, cchLine, pchLine);
     2897                fRet |= rc != VINF_SUCCESS;
     2898                ScmVerbose(pState, 2, "line %u: #ifndef %.*s\n", ScmStreamTellLine(pIn) - 1, Guard.cch, Guard.psz);
     2899
     2900                /* #define xxxx */
     2901                pchLine = ScmStreamGetLine(pIn, &cchLine, &enmEol);
     2902                if (!pchLine)
     2903                    return ScmError(pState, VERR_PARSE_ERROR, "%u: Unexpected end of file after '#ifndef %.*s'\n",
     2904                                    ScmStreamTellLine(pIn) - 1, Guard.cch, Guard.psz);
     2905                const SCMMATCHWORD aDefineGuard[] =
     2906                {
     2907                    { RT_STR_TUPLE("#"),                0, true, false },
     2908                    { RT_STR_TUPLE("define"),           0, true, false },
     2909                    { Guard.psz, (uint8_t)Guard.cch,    1, true, false },
     2910                    { RT_STR_TUPLE(""),                 0, true, false },
     2911                };
     2912                rc = ScmMatchWords(pchLine, cchLine, aDefineGuard, RT_ELEMENTS(aDefineGuard),
     2913                                   NULL /*poffNext*/, NULL /*paIdentifiers*/, RTErrInfoInitStatic(&ErrInfo));
     2914                if (RT_FAILURE(rc))
     2915                    return ScmError(pState, rc, "%u: Expected '#define %.*s' to follow '#ifndef %.*s'. %s (%.*s)\n",
     2916                                    ScmStreamTellLine(pIn) - 1, Guard.cch, Guard.psz, Guard.cch, Guard.psz,
     2917                                    ErrInfo.Core.pszMsg, cchLine, pchLine);
     2918                fRet |= rc != VINF_SUCCESS;
     2919
     2920                /*
     2921                 * Write guard, making sure we've got a single blank line preceeding it.
     2922                 */
     2923                ScmStreamPutEol(pOut, enmEol);
     2924                ScmStreamWrite(pOut, RT_STR_TUPLE("#ifndef "));
     2925                ScmStreamWrite(pOut, Guard.psz, Guard.cch);
     2926                ScmStreamPutEol(pOut, enmEol);
     2927                ScmStreamWrite(pOut, RT_STR_TUPLE("#define "));
     2928                ScmStreamWrite(pOut, Guard.psz, Guard.cch);
     2929                rc = ScmStreamPutEol(pOut, enmEol);
     2930                if (RT_FAILURE(rc))
     2931                    return false;
     2932                break;
     2933            }
     2934        }
     2935
     2936        if (!isBlankLine(pchLine, cchLine))
     2937        {
     2938            while (cBlankLines-- > 0)
     2939                ScmStreamPutEol(pOut, enmEol);
     2940            cBlankLines = 0;
     2941            rc = ScmStreamPutLine(pOut, pchLine, cchLine, enmEol);
     2942            if (RT_FAILURE(rc))
     2943                return false;
     2944        }
     2945        else
     2946            cBlankLines++;
     2947    }
     2948
     2949    /*
     2950     * Look for pragma once wrapped in #ifndef RT_WITHOUT_PRAGMA_ONCE.
     2951     */
     2952    size_t const iPragmaOnce = ScmStreamTellLine(pIn);
     2953    static const SCMMATCHWORD s_aIfndefRtWithoutPragmaOnce[] =
     2954    {
     2955        { RT_STR_TUPLE("#"),                        0, true, false },
     2956        { RT_STR_TUPLE("ifndef"),                   0, true, false },
     2957        { RT_STR_TUPLE("RT_WITHOUT_PRAGMA_ONCE"),   1, true, false },
     2958        { RT_STR_TUPLE(""),                         0, true, false },
     2959    };
     2960    static const SCMMATCHWORD s_aPragmaOnce[] =
     2961    {
     2962        { RT_STR_TUPLE("#"),                        0, true, false },
     2963        { RT_STR_TUPLE("pragma"),                   0, true, false },
     2964        { RT_STR_TUPLE("once"),                     1, true, false},
     2965        { RT_STR_TUPLE(""),                         0, true, false },
     2966    };
     2967    static const SCMMATCHWORD s_aEndif[] =
     2968    {
     2969        { RT_STR_TUPLE("#"),                        0, true, false },
     2970        { RT_STR_TUPLE("endif"),                    0, true, false },
     2971        { RT_STR_TUPLE(""),                         0, true, false },
     2972    };
     2973
     2974    /* #ifndef RT_WITHOUT_PRAGMA_ONCE */
     2975    pchLine = ScmStreamGetLine(pIn, &cchLine, &enmEol);
     2976    if (!pchLine)
     2977        return ScmError(pState, VERR_PARSE_ERROR, "%u: Unexpected end of file after header guard!\n", iPragmaOnce + 1);
     2978    size_t offNext;
     2979    rc = ScmMatchWords(pchLine, cchLine, s_aIfndefRtWithoutPragmaOnce, RT_ELEMENTS(s_aIfndefRtWithoutPragmaOnce),
     2980                       &offNext, NULL /*paIdentifiers*/, RTErrInfoInitStatic(&ErrInfo));
     2981    if (RT_SUCCESS(rc))
     2982    {
     2983        fRet |= rc != VINF_SUCCESS;
     2984        if (offNext != cchLine)
     2985            return ScmError(pState, VERR_PARSE_ERROR, "%u: Characters trailing '#ifndef RT_WITHOUT_PRAGMA_ONCE' (%.*s)\n",
     2986                            iPragmaOnce + 1, cchLine, pchLine);
     2987
     2988        /* # pragma once */
     2989        pchLine = ScmStreamGetLine(pIn, &cchLine, &enmEol);
     2990        if (!pchLine)
     2991            return ScmError(pState, VERR_PARSE_ERROR, "%u: Unexpected end of file after '#ifndef RT_WITHOUT_PRAGMA_ONCE'\n",
     2992                            iPragmaOnce + 2);
     2993        rc = ScmMatchWords(pchLine, cchLine, s_aPragmaOnce, RT_ELEMENTS(s_aPragmaOnce),
     2994                           NULL /*poffNext*/, NULL /*paIdentifiers*/, RTErrInfoInitStatic(&ErrInfo));
     2995        if (RT_SUCCESS(rc))
     2996            fRet |= rc != VINF_SUCCESS;
     2997        else
     2998            return ScmError(pState, rc, "%u: Expected '# pragma once' to follow '#ifndef RT_WITHOUT_PRAGMA_ONCE'! %s (%.*s)\n",
     2999                            iPragmaOnce + 2, ErrInfo.Core.pszMsg, cchLine, pchLine);
     3000
     3001        /* #endif */
     3002        pchLine = ScmStreamGetLine(pIn, &cchLine, &enmEol);
     3003        if (!pchLine)
     3004            return ScmError(pState, VERR_PARSE_ERROR, "%u: Unexpected end of file after '#ifndef RT_WITHOUT_PRAGMA_ONCE' and '#pragma once'\n",
     3005                            iPragmaOnce + 3);
     3006        rc = ScmMatchWords(pchLine, cchLine, s_aEndif, RT_ELEMENTS(s_aEndif),
     3007                           NULL /*poffNext*/, NULL /*paIdentifiers*/, RTErrInfoInitStatic(&ErrInfo));
     3008        if (RT_SUCCESS(rc))
     3009            fRet |= rc != VINF_SUCCESS;
     3010        else
     3011            return ScmError(pState, rc,
     3012                            "%u: Expected '#endif' to follow '#ifndef RT_WITHOUT_PRAGMA_ONCE' and '# pragma once'! %s (%.*s)\n",
     3013                            iPragmaOnce + 3, ErrInfo.Core.pszMsg, cchLine, pchLine);
     3014        ScmVerbose(pState, 3, "Found pragma once\n");
     3015    }
     3016    else
     3017    {
     3018        rc = ScmStreamSeekByLine(pIn, iPragmaOnce);
     3019        if (RT_FAILURE(rc))
     3020            return ScmError(pState, rc, "seek error\n");
     3021        fRet = true;
     3022        ScmVerbose(pState, 2, "Missing #pragma once\n");
     3023    }
     3024
     3025    /*
     3026     * Write the pragma once stuff.
     3027     */
     3028    ScmStreamPutLine(pOut, RT_STR_TUPLE("#ifndef RT_WITHOUT_PRAGMA_ONCE"), enmEol);
     3029    ScmStreamPutLine(pOut, RT_STR_TUPLE("# pragma once"), enmEol);
     3030    rc = ScmStreamPutLine(pOut, RT_STR_TUPLE("#endif"), enmEol);
     3031    if (RT_FAILURE(rc))
     3032        return false;
     3033
     3034    /*
     3035     * Copy the rest of the file and remove pragma once statements, while
     3036     * looking for the last #endif in the file.
     3037     */
     3038    size_t iEndIf = 0;
     3039    while ((pchLine = ScmStreamGetLine(pIn, &cchLine, &enmEol)) != NULL)
     3040    {
     3041        if (cchLine > 2)
     3042        {
     3043            const char *pchHash = (const char *)memchr(pchLine, '#', cchLine);
     3044            if (    pchHash
     3045                && isSpanOfBlanks(pchLine, pchHash - pchLine))
     3046            {
     3047                size_t off = pchHash - pchLine + 1;
     3048                while (off < cchLine && RT_C_IS_BLANK(pchLine[off]))
     3049                    off++;
     3050                /* #pragma once */
     3051                if (off + sizeof("pragma") < cchLine && !memcmp(&pchLine[off], RT_STR_TUPLE("pragma")))
     3052                {
     3053                    rc = ScmMatchWords(pchLine, cchLine, s_aPragmaOnce, RT_ELEMENTS(s_aPragmaOnce),
     3054                                       &offNext, NULL /*paIdentifiers*/, RTErrInfoInitStatic(&ErrInfo));
     3055                    if (RT_SUCCESS(rc))
     3056                    {
     3057                        fRet = true;
     3058                        continue;
     3059                    }
     3060                }
     3061                /* #endif */
     3062                else if (off + sizeof("endif") < cchLine && !memcmp(&pchLine[off], RT_STR_TUPLE("endif")))
     3063                    iEndIf = ScmStreamTellLine(pOut);
     3064            }
     3065        }
     3066
     3067        rc = ScmStreamPutLine(pOut, pchLine, cchLine, enmEol);
     3068        if (RT_FAILURE(rc))
     3069            return false;
     3070    }
     3071
     3072    /*
     3073     * Check out the last endif, making sure it's well formed and make sure it has the
     3074     * right kind of comment following it.
     3075     */
     3076    /** @todo \#endif */
     3077
     3078    return fRet;
     3079}
     3080
     3081
    27533082/**
    27543083 * Rewrite a C/C++ source or header file.
  • trunk/src/bldprogs/scmstream.cpp

    r76451 r76506  
    241241    pStream->fFullyLineated = true;
    242242    pStream->rc             = VINF_SUCCESS;
     243
     244    /* Initialize the first line with a zero length so ScmStreamWrite won't misbehave. */
     245    if (pStream->cLinesAllocated == 0)
     246        scmStreamGrowLines(pStream, 1);
     247    if (pStream->cLinesAllocated > 0)
     248    {
     249        pStream->paLines[0].off    = 0;
     250        pStream->paLines[0].cch    = 0;
     251        pStream->paLines[0].enmEol = SCMEOL_NONE;
     252    }
    243253}
    244254
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette