[osg-submissions] Handling Empty/NULL strings in ShapeAttributeList

John Vidar Larring larring at weatherone.tv
Thu Jun 19 06:20:43 PDT 2008


Thanks Robert, works for me:)

-- John

Robert Osfield wrote:
> Hi John,
> 
> What I have gone for is to convert ShapeAttribute::_string usage so
> that it uses strdup and free rather than the previous awkward new
> char[] copy code path.  The new code stores a null pointer when a null
> value is passed in.  This could possible break other code if it
> assumes that _string is never null, but if this is the case then this
> code itself is broken and needs fixing.
> 
> I have now checked in this change, but don't have any problematic
> files to test against.  Could you send me one?  Or do an svn checkout
> and let me know how you get on.
> 
> Cheers,
> Robert.
> 
> On Wed, Jun 18, 2008 at 2:42 PM, Robert Osfield
> <robert.osfield at gmail.com> wrote:
>> Hi John,
>>
>> Reviewing the fix, it strikes me that the code should probably be
>> something like:
>>
>> ShapeAttribute::ShapeAttribute(const char * name, const char * value) :
>>    _name(name),
>>    _type(STRING)
>> {
>>   if (value) _string = strdup(value);
>>   else // some kind of fallback
>> }
>>
>> A null name would also be potential problem for the ShapeAttribute code.
>>
>> Thoughts?
>>
>> Robert.
>>
>>
>> On Thu, Jun 12, 2008 at 3:59 PM, John Vidar Larring
>> <larring at weatherone.tv> wrote:
>>> Hi All,
>>>
>>> Short version:
>>> --------------
>>>
>>> Problem: Empty string value in an osgSim::ShapeAttributeList causes SIGSEV
>>> when loading a .osg file.
>>>
>>> Solution: Changing line 47 in src/osgSim/ShapeAttribute.cpp from:
>>> -    std::string str(value);
>>> +    std::string str((value ? value : ""));
>>>
>>> Attached file is a modification of src/osgSim/ShapeAttribute.cpp in svn
>>> revision 8426.
>>>
>>> Long version (including context):
>>> ---------------------------------
>>>
>>> osgGIS now allows the user to keep meta-data when converting ESRI Shape
>>> files to OSG graph:
>>>
>>> osggis: world.shp -> world.osg:
>>> [...snip...]
>>>                Geode {
>>>                  UserData {
>>>                    osgSim::ShapeAttributeList {
>>>                      string "cntry_name" "Antarctica"
>>>                      int    "colormap" 7
>>>                      string "curr_code" "NCIC"
>>>                      string "curr_type" ""
>>>                      string "fips_cntry" "AY"
>>>                      string "gmi_cntry" "ATA"
>>>                      string "iso_2digit" "AQ"
>>>                      string "iso_3digit" "ATA"
>>>                      string "landlocked" "N"
>>>                      string "long_name" "Antarctica"
>>>                      int    "pop_cntry" -99999
>>>                      string "sovereign" "Antarctica"
>>>                      double "sqkm" 1.23031e+07
>>>                      double "sqmi" 4.75021e+06
>>>                    }
>>>                  }
>>> [...snip...]
>>>
>>> ...which is parallell to what 'osgconv world.shp world.osg' produces:
>>> [...snip...]
>>>  Geometry {
>>>    DataVariance STATIC
>>>    UserData {
>>>      osgSim::ShapeAttributeList {
>>>        string "FIPS_CNTRY" "AY"
>>>        string "GMI_CNTRY" "ATA"
>>>        string "ISO_2DIGIT" "AQ"
>>>        string "ISO_3DIGIT" "ATA"
>>>        string "CNTRY_NAME" "Antarctica
>>>
>>>                                                                      "
>>>        string "LONG_NAME" "Antarctica                              "
>>>        string "SOVEREIGN" "Antarctica                              "
>>>        int    "POP_CNTRY" -99999
>>>        string "CURR_TYPE" "                "
>>>        string "CURR_CODE" "NCIC"
>>>        string "LANDLOCKED" "N"
>>>        int    "SQKM" 12303052
>>>        int    "SQMI" 4750207
>>>        int    "COLORMAP" 7
>>>      }
>>>    }
>>> [...snip...]
>>>
>>> The difference is that osgconv (a.k.a. shp plugin) adds whitespace to string
>>> "curr_type" while osggis does not. However, the output from osggis is
>>> cleaner and should IMHO be acceptable.
>>>
>>> However, osgDB::Input in ShapeAttributeList_readLocalData converts the empty
>>> string to a NULL pointer:
>>>
>>> bool ShapeAttributeList_readLocalData(osg::Object &obj, osgDB::Input &fr)
>>> {
>>>    bool iteratorAdvanced = false;
>>>    ShapeAttributeList &sal = static_cast<ShapeAttributeList &>(obj);
>>>
>>>    int entry = fr[0].getNoNestedBrackets();
>>>
>>>    while (!fr.eof() && fr[0].getNoNestedBrackets()>=entry)
>>>    {
>>>        if (fr.matchSequence("string %s %s"))
>>>        {
>>>            sal.push_back(osgSim::ShapeAttribute(fr[1].getStr(),
>>> fr[2].getStr()));  <<== fr[2].getStr() returns NULL for 'string "curr_type"
>>> ""'
>>>            fr += 3;
>>>            iteratorAdvanced = true;
>>>        }
>>> [...snip...]
>>>
>>> This results in a SIGSEV in ShapeAttribute::ShapeAttribute(const char *
>>> name, const char * value) with the following stack trace:
>>>
>>> #0  0x00000030a032e25d in raise () from /lib64/tls/libc.so.6
>>> #1  0x00000030a032fa5e in abort () from /lib64/tls/libc.so.6
>>> #2  0x00000030a28b1148 in __gnu_cxx::__verbose_terminate_handler () from
>>> /usr/lib64/libstdc++.so.6
>>> #3  0x00000030a28af176 in __cxa_call_unexpected () from
>>> /usr/lib64/libstdc++.so.6
>>> #4  0x00000030a28af1a3 in std::terminate () from /usr/lib64/libstdc++.so.6
>>> #5  0x00000030a28af2a3 in __cxa_throw () from /usr/lib64/libstdc++.so.6
>>> #6  0x00000030a2851bf0 in std::__throw_logic_error () from
>>> /usr/lib64/libstdc++.so.6
>>> #7  0x00000030a2892706 in std::basic_string<char, std::char_traits<char>,
>>> std::allocator<char> >::basic_string$base () from /usr/lib64/libstdc++.so.6
>>> #8  0x00000030a28927b3 in std::basic_string<char, std::char_traits<char>,
>>> std::allocator<char> >::basic_string () from /usr/lib64/libstdc++.so.6
>>> #9  0x0000002a96c9c2d7 in osgSim::ShapeAttribute::ShapeAttribute () at
>>> /usr/lib/gcc/x86_64-redhat-linux/3.4.6/../../../../include/c++/3.4.6/bits/locale_facets.tcc:2443
>>> #10 0x0000002a98083d16 in ShapeAttributeList_readLocalData (obj=@0x5601c0,
>>> fr=@0x7fbfffdde0) at
>>> /home/john/external.el4/OpenSceneGraph/trunk/src/osgPlugins/osgSim/IO_ShapeAttribute.cpp:38
>>> #11 0x0000002a95cab5b0 in osgDB::Registry::readObject (this=0x51ac90,
>>> dowMap=@0x51acc8, fr=@0x7fbfffdde0) at
>>> /home/john/external.el4/OpenSceneGraph/trunk/src/osgDB/Registry.cpp:1003
>>> #12 0x0000002a95cab78a in osgDB::Registry::readObject (this=0x51ac90,
>>> fr=@0x7fbfffdde0) at
>>> /home/john/external.el4/OpenSceneGraph/trunk/src/osgDB/Registry.cpp:1036
>>>
>>> The attached file fixes the problem by testing for NULL pointer value in
>>>  ShapeAttribute::ShapeAttribute.
>>>
>>> Best regards,
>>> John
>>>
>>> --
>>> This message has been scanned for viruses and
>>> dangerous content by MailScanner, and is
>>> believed to be clean.
>>>
>>>
>>> _______________________________________________
>>> osg-submissions mailing list
>>> osg-submissions at lists.openscenegraph.org
>>> http://lists.openscenegraph.org/listinfo.cgi/osg-submissions-openscenegraph.org
>>>
>>>
> _______________________________________________
> osg-submissions mailing list
> osg-submissions at lists.openscenegraph.org
> http://lists.openscenegraph.org/listinfo.cgi/osg-submissions-openscenegraph.org
> 


-- 
Best regards,
John
WeatherOne


-- 
This message has been scanned for viruses and
dangerous content by MailScanner, and is
believed to be clean.



More information about the osg-submissions mailing list