Commit 558af6d7 authored by Dick Hollenbeck's avatar Dick Hollenbeck
Browse files

add EscapedUTF8() and revise ReadDelimitedText() to complement it

parent 90dc2908
Loading
Loading
Loading
Loading
+59 −17
Original line number Diff line number Diff line
@@ -8,32 +8,74 @@
#include "kicad_string.h"


/* read a double-quote delimited text from source and put it in in dest,
 *  read NbMaxChar bytes max
 *  return the char count read from source
 */
int ReadDelimitedText( char* dest, char* source, int NbMaxChar )
int  ReadDelimitedText( char* aDest, const char* aSource, int aDestSize )
{
    if( aDestSize <= 0 )
        return 0;

    bool    inside = false;
    char*   start = aDest;
    char*   limit = aDest + aDestSize - 1;
    char    cc;

    while( (cc = *aSource++) != 0 && aDest < limit )
    {
        if( cc == '\\' )
        {
            cc = *aSource++;

            if( inside )
                *aDest++ = cc;
        }

        else if( cc == '"' )
        {
            if( inside )
                break;          // 2nd double quote is end of delimited text

            inside = true;      // first delimiter found, make note, do not copy
        }

        else if( inside )
        {
    int ii, jj, flag = 0;
            *aDest++ = cc;
        }
    }

    *aDest = 0;

    return aDest - start;
}


    for( ii = 0, jj = 0; ii < NbMaxChar - 1; jj++, source++ )
std::string EscapedUTF8( const wxString& aString )
{
        if( *source == 0 )
            break;                      /* E.O.L. */
        if( *source == '"' )            /* delimiter is " */
    std::string utf8 = TO_UTF8( aString );

    std::string ret;

    // ret += '"';

    for( std::string::const_iterator it = utf8.begin();  it!=utf8.end();  ++it )
    {
            if( flag )
                break;                  /* End of delimited text */
            flag = 1;                   /* First delimiter found. */
        // this escaping strategy is designed to be compatible with ReadDelimitedText():
        if( *it == '"' )
        {
            ret += '\\';
            ret += '"';
        }
        else if( flag )
        else if( *it == '\\' )
        {
            *dest = *source; dest++; ii++;
            ret += '\\';    // double it up
            ret += '\\';
        }
        else
            ret += *it;
    }

    *dest = 0;  /* Null terminated */
    return jj;
    // ret += '"';

    return ret;
}


+25 −7
Original line number Diff line number Diff line
@@ -14,14 +14,32 @@
char*    strupper( char* Text );
char*    strlower( char* Text );

/* Read string delimited with (") character.
 * Upload NbMaxChar max
 * Returns the number of codes read in source
 * dest is terminated by NULL

/**
 * Function ReadDelimitedText
 * extracts bytes from @a aSource delimited string segment to @a aDest buffer.
 * The extracted string will be null terminated even if truncation is necessary
 * because aDestSize was not large enough.
 *
 * @param aDest is the destination byte buffer.
 * @param aSource is the source bytes as a C string.
 * @param aDestSize is the size of the destination byte buffer.
 * @return int - the number of bytes extracted.
 */
int      ReadDelimitedText( char* dest,
                            char* source,
                            int   NbMaxChar );
int  ReadDelimitedText( char* aDest, const char* aSource, int aDestSize );


/**
 * Function EscapedUTF8
 * returns an 8 bit UTF8 string given aString in unicode form.
 * Any double quoted or back slashes are prefixed with a '\\' byte and the form
 * of this UTF8 byte string is compatible with function ReadDelimitedText().
 *
 * @param aString is the input string to convert.
 * @return std::string - the escaped input text, without the wrapping double quotes.
 */
std::string EscapedUTF8( const wxString& aString );


/* Read one line line from a file.
 * Returns the first useful line read by eliminating blank lines and comments.
+1 −1
Original line number Diff line number Diff line
@@ -7,7 +7,7 @@

# It is here to assist Dick with verifying compilation of /new stuff with mingw (under linux)

set( CMAKE_SYSTEM_NAME Linux )
set( CMAKE_SYSTEM_NAME Windows )

#-----<configuration>-----------------------------------------------

+17 −13
Original line number Diff line number Diff line
@@ -80,31 +80,31 @@ void TEXTE_PCB::Copy( TEXTE_PCB* source )
 */
int TEXTE_PCB::ReadTextePcbDescr( LINE_READER* aReader )
{
    char* Line;
    char* line;
    char  text[1024];
    char  style[256];

    while( aReader->ReadLine() )
    {
        Line = aReader->Line();
        if( strnicmp( Line, "$EndTEXTPCB", 11 ) == 0 )
        line = aReader->Line();
        if( strnicmp( line, "$EndTEXTPCB", 11 ) == 0 )
            return 0;
        if( strncmp( Line, "Te", 2 ) == 0 ) /* Text line (first line for multi line texts */
        if( strncmp( line, "Te", 2 ) == 0 ) /* Text line (first line for multi line texts */
        {
            ReadDelimitedText( text, Line + 2, sizeof(text) );
            ReadDelimitedText( text, line + 2, sizeof(text) );
            m_Text = CONV_FROM_UTF8( text );
            continue;
        }
        if( strncmp( Line, "nl", 2 ) == 0 ) /* next line of the current text */
        if( strncmp( line, "nl", 2 ) == 0 ) /* next line of the current text */
        {
            ReadDelimitedText( text, Line + 2, sizeof(text) );
            ReadDelimitedText( text, line + 2, sizeof(text) );
            m_Text.Append( '\n' );
            m_Text += CONV_FROM_UTF8( text );
            continue;
        }
        if( strncmp( Line, "Po", 2 ) == 0 )
        if( strncmp( line, "Po", 2 ) == 0 )
        {
            sscanf( Line + 2, " %d %d %d %d %d %d",
            sscanf( line + 2, " %d %d %d %d %d %d",
                    &m_Pos.x, &m_Pos.y, &m_Size.x, &m_Size.y,
                    &m_Thickness, &m_Orient );

@@ -115,11 +115,11 @@ int TEXTE_PCB::ReadTextePcbDescr( LINE_READER* aReader )
                m_Size.y = 5;
            continue;
        }
        if( strncmp( Line, "De", 2 ) == 0 )
        if( strncmp( line, "De", 2 ) == 0 )
        {
            style[0] = 0;
            int normal_display = 1;
            sscanf( Line + 2, " %d %d %lX %s\n", &m_Layer, &normal_display,
            sscanf( line + 2, " %d %d %lX %s\n", &m_Layer, &normal_display,
                    &m_TimeStamp, style );

            m_Mirror = normal_display ? false : true;
@@ -157,18 +157,22 @@ bool TEXTE_PCB::Save( FILE* aFile ) const
    const char* style = m_Italic ? "Italic" : "Normal";

    wxArrayString* list = wxStringSplit( m_Text, '\n' );

    for( unsigned ii = 0; ii < list->Count(); ii++ )
    {
        wxString txt  = list->Item( ii );

        if ( ii == 0 )
            fprintf( aFile, "Te \"%s\"\n", CONV_TO_UTF8( txt ) );
            fprintf( aFile, "Te \"%s\"\n", EscapedUTF8( txt ).c_str() );
        else
            fprintf( aFile, "nl \"%s\"\n", CONV_TO_UTF8( txt ) );
    }
    delete (list);

    delete list;

    fprintf( aFile, "Po %d %d %d %d %d %d\n",
             m_Pos.x, m_Pos.y, m_Size.x, m_Size.y, m_Thickness, m_Orient );

    fprintf( aFile, "De %d %d %lX %s\n", m_Layer,
             m_Mirror ? 0 : 1,
             m_TimeStamp, style );
+2 −4
Original line number Diff line number Diff line
@@ -327,13 +327,11 @@ int WinEDA_BasePcbFrame::ReadSetup( LINE_READER* aReader )
            }
            catch( IO_ERROR& e )
            {
#if 1
                wxString msg;
                msg.Printf( wxT( "Error reading PcbPlotParams from %s:\n%s" ),
                msg.Printf( _( "Error reading PcbPlotParams from %s:\n%s" ),
                            aReader->GetSource().GetData(),
                            e.errorText.GetData() );
                wxMessageBox( msg, wxT( "Open Board File" ), wxICON_ERROR );
#endif
                wxMessageBox( msg, _( "Open Board File" ), wxICON_ERROR );
            }

            continue;