AnsweredAssumed Answered

EXC_BAD_ACCESS (code=EXC_I386_GPFLT) on app foreground

Question asked by jacob.shapley@dfw.wa.gov on May 11, 2018
Latest reply on May 16, 2018 by jacob.shapley@dfw.wa.gov

I've been chasing this bug for weeks. Getting crash due to EXC_BAD_ACCESS (code=EXC_I386_GPFLT) frequently (~25% of the time) when backgrounding and re-foregrounding iOS app. We are using iOS Runtime 100.2.1. Crash is occurring across device types and iOS versions. Any help in identifying a workaround would be appreciated.

 

Our implementation:

1) all tables and layers instantiated from local runtime replica geodatabase (regsGDB.geodatabase):

    fileprivate func initGDB() -> Void {

        self.deinitGDB()

        regsGDB = AGSGeodatabase(fileURL: FileUtil.urlFor(GlobalConstants.fileNames.REGS_WORKING_GDB)!)

        regsGDB.load(completion: {[weak self] (error: Error?) in

            if (error != nil) {

                self?.regsGDBLoaded = false

                self?.disableFeatureInteraction()

                os_log("Error loading geodatabase", [error?.localizedDescription])

            } else {

                self?.loadLayers()

            }})

    }

 

2) strong references to tables and layers, with nil checks on regsGDB before calling load (for tables and layers):

fileprivate func loadLayers() -> Void {

        if regsGDB != nil && regsGDB.loadStatus == .loaded {

            self.countiesTable = (regsGDB.geodatabaseFeatureTable(byServiceLayerID: GlobalConstants.IDs.COUNTIES_LAYER_INDEX)!) as AGSFeatureTable

            self.countiesLayer = AGSFeatureLayer(featureTable: (self.countiesTable)!)

            self.countiesLayer.renderer = EsriUtil.municipalityPolyRenderer

            self.countiesLayer.labelsEnabled = true

            self.countiesLayer.selectionColor = UIColor.cyan

            self.countiesLayer.selectionWidth = 5

            self.countiesLayer.minScale = 6000000

            self.map.operationalLayers.add(self.countiesLayer)

            

            self.citiesTable = (regsGDB.geodatabaseFeatureTable(byServiceLayerID: GlobalConstants.IDs.CITIES_LAYER_INDEX)!) as AGSFeatureTable

            self.citiesLayer = AGSFeatureLayer(featureTable: (self.citiesTable)!)

            self.citiesLayer.renderer = EsriUtil.municipalityPolyRenderer

            self.citiesLayer.labelsEnabled = true

            self.citiesLayer.selectionColor = UIColor.cyan

            self.citiesLayer.selectionWidth = 5

            self.citiesLayer.minScale = 6000000

            self.map.operationalLayers.add(self.citiesLayer)

.

.

.

 

3) deinit by manually removing all operationalLayers and tables, nilling out all layers and tables prior to reinitializing and loading gdb, tables and layers: 

fileprivate func deinitGDB() -> Void {

        // remove and nil out the layers

        self.map.operationalLayers.removeAllObjects()

        self.countiesLayer = nil

        self.citiesLayer = nil

       .

       .

       .

        // remove and nil out the tables

        self.map.tables.removeAllObjects()

        self.countiesTable = nil

        self.citiesTable = nil

       .

       .

       .

        if regsGDB != nil {

            switch regsGDB.loadStatus {

            case .loading:

                regsGDB.cancelLoad()

                break

            default:

                break

            }

            regsGDB.close()

        }

        regsGDBLoaded = false

    }

 

 

I have not been able to reproduce by stepping through/over. Thoughts?

 

Attached is a debug log of ObjC and C++ Exceptions encountered on foregrounding repeatedly in the same session. Note, crash only occurs when breakpoints are turned off (see crash again in last backtrace in this file).

 

 

Here's a back-trace of the crash (full stack is attached):

 

* thread #67, queue = 'com.apple.root.default-qos', stop reason = EXC_BAD_ACCESS (code=EXC_I386_GPFLT)

  * frame #0: 0x000000010f2574b4 ArcGIS`columnMem + 88

    frame #1: 0x000000010f257535 ArcGIS`ags_sqlite3_column_bytes + 15

    frame #2: 0x000000010e87a38d ArcGIS`Esri_runtimecore::Geodatabase::Sqlite_command::get_as_text(int) + 77

    frame #3: 0x000000010e81287e ArcGIS`Esri_runtimecore::Geodatabase::Bound_row_value::operator std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >() const + 28

    frame #4: 0x000000010e848b6d ArcGIS`Esri_runtimecore::Geodatabase::populate_field_definitions(std::__1::shared_ptr<Esri_runtimecore::Geodatabase::Database>, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >) + 503

    frame #5: 0x000000010e814079 ArcGIS`Esri_runtimecore::Geodatabase::Catalog_dataset::get_item_definition(Esri_runtimecore::Geodatabase::Catalog_item_reference const&) + 2825

    frame #6: 0x000000010e890fce ArcGIS`Esri_runtimecore::Geodatabase::Details::Table_schema::describe(std::__1::shared_ptr<Esri_runtimecore::Geodatabase::Database>&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&) + 232

    frame #7: 0x000000010e891aab ArcGIS`Esri_runtimecore::Geodatabase::Details::Table_schema::open(std::__1::shared_ptr<Esri_runtimecore::Geodatabase::Database>&, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&) + 191

    frame #8: 0x000000010e8ad763 ArcGIS`std::__1::shared_ptr<Esri_runtimecore::Geodatabase::Table> Esri_runtimecore::Geodatabase::Database::open<Esri_runtimecore::Geodatabase::Table>(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&) + 51

    frame #9: 0x000000010da7a276 ArcGIS`Esri_runtimecore::Mapping::Geodatabase_feature_table::load_sync(pplx::cancellation_token) + 206

    frame #10: 0x000000010da7cc3a ArcGIS`std::__1::__function::__func<Esri_runtimecore::Mapping::Geodatabase_feature_table::load_or_retry_(Esri_runtimecore::Mapping::Loadable::Load_or_retry_mode)::$_2, std::__1::allocator<Esri_runtimecore::Mapping::Geodatabase_feature_table::load_or_retry_(Esri_runtimecore::Mapping::Loadable::Load_or_retry_mode)::$_2>, void ()>::operator()() + 150

    frame #11: 0x000000010db748b2 ArcGIS`std::__1::__function::__func<Esri_runtimecore::Mapping::Task<void>::Task(std::__1::function<void ()>, pplx::cancellation_token_source)::'lambda'(), std::__1::allocator<Esri_runtimecore::Mapping::Task<void>::Task(std::__1::function<void ()>, pplx::cancellation_token_source)::'lambda'()>, boost::any ()>::operator()() + 18

    frame #12: 0x000000010deeb4fb ArcGIS`std::__1::function<boost::any ()>::operator()() const + 27

    frame #13: 0x000000010deeb75e ArcGIS`std::__1::__function::__func<Esri_runtimecore::Mapping::Task_implementation::Task_implementation(std::__1::function<boost::any ()>, Esri_runtimecore::Mapping::Task_options)::$_0, std::__1::allocator<Esri_runtimecore::Mapping::Task_implementation::Task_implementation(std::__1::function<boost::any ()>, Esri_runtimecore::Mapping::Task_options)::$_0>, boost::any ()>::operator()() + 50

    frame #14: 0x000000010deeb4fb ArcGIS`std::__1::function<boost::any ()>::operator()() const + 27

    frame #15: 0x000000010deeb28f ArcGIS`pplx::details::_PPLTaskHandle<boost::any, pplx::task<boost::any>::_InitialTaskHandle<boost::any, Esri_runtimecore::Mapping::Task_implementation::Task_implementation(std::__1::function<boost::any ()>, Esri_runtimecore::Mapping::Task_options)::$_0, pplx::details::_TypeSelectorNoAsync>, pplx::details::_TaskProcHandle>::invoke() const + 267

    frame #16: 0x000000010f55d5c4 ArcGIS`pplx::details::_TaskProcHandle::_RunChoreBridge(void*) + 16

    frame #17: 0x000000010ee1b428 ArcGIS`Esri_runtimecore::Common::Core_scheduler::invoke_(Esri_runtimecore::Common::Core_scheduler::Queued_proc*) + 24

    frame #18: 0x000000010ee1b3d0 ArcGIS`Esri_runtimecore::Common::Core_scheduler::Queued_proc::invoke() + 48

    frame #19: 0x000000010ee1ad1f ArcGIS`Esri_runtimecore::Common::Core_scheduler::bridge_proc_(void*) + 23

    frame #20: 0x0000000119e8a848 libdispatch.dylib`_dispatch_client_callout + 8

    frame #21: 0x0000000119e8f675 libdispatch.dylib`_dispatch_queue_override_invoke + 1451

    frame #22: 0x0000000119e963c8 libdispatch.dylib`_dispatch_root_queue_drain + 664

    frame #23: 0x0000000119e960d2 libdispatch.dylib`_dispatch_worker_thread3 + 132

    frame #24: 0x000000011c615169 libsystem_pthread.dylib`_pthread_wqthread + 1387

    frame #25: 0x000000011c614be9 libsystem_pthread.dylib`start_wqthread + 13

(lldb)

 

 

Outcomes