file.write issues with mode "w+b" using SD
Posted: Sun Dec 01, 2024 10:12 am
Using ESP32S3 rev2 board on windows Arduino IDE.
I am creating a port to osgeo shapelib [1, 2]. My port lives here [3]. The library reads and creates shapefiles to extract geographical information (GIS vector layers) such as polygon maps, GPS points, polylines, etc. I modified the library to work with the SD library reading files from the SD card. The reading part works great so far. Maybe it is enough to be able to read with esp32. However, I want to push it a bit forward, and I also want to achieve the writing functionality.
The problem is:
Guru Meditation Error: Core 1 panic'ed (LoadProhibited). Exception was unhandled.
After some debugging, I found out that the problem occurs when a file.write runs with mode "w+b". Particularly here:
if (psSHP->sHooks.FWrite(pabyRec, nRecordSize, 1, psSHP->fpSHP) < 1) // https://github.com/aferust/ShapeLibForE ... .cpp#L1757
which invokes this function:
[https://github.com/aferust/ShapeLibForE ... ks.cpp#L33]
...
SAOffset SADFWrite(const void *p, SAOffset size, SAOffset nmemb, SAFile &file)
{
size_t bytesWritten = file.write((const uint8_t *)p, size * nmemb); // problem here
...
Of course, I checked if there are null or unallocated buffers, but everything is what it is supposed to be. I am stuck in this problem and need help.
Thanks in advance!
1: http://shapelib.maptools.org/
2: https://github.com/OSGeo/shapelib
3: https://github.com/aferust/ShapeLibForESP32
A test code to reproduce the problem:
```
#include "shapefil.hpp"
#include "SD.h"
void setup() {
Serial.begin(115200);
if (!SD.begin()) {
Serial.println("Card Mount Failed");
return;
}
SHPsetFileSystem(SD);
// Open SHP and DBF files for writing
SHPHandle hSHP = SHPCreate("/p1.shp", SHPT_POLYGON);
//DBFHandle hDBF = DBFCreate("/p1.dbf");
if (hSHP == nullptr /*|| hDBF == nullptr*/) {
Serial.println("Failed to create SHP or DBF file!");
return;
}
/*
// Add a field to the DBF file
if (DBFAddField(hDBF, "Name", FTString, 20, 0) == -1) {
Serial.println("Failed to add field to DBF!");
return;
}
*/
// Create a polygon
double xCoords[] = {0.0, 1.0, 1.0, 0.0, 0.0}; // X coordinates
double yCoords[] = {0.0, 0.0, 1.0, 1.0, 0.0}; // Y coordinates
int partStart[] = {0}; // One part starting at index 0
SHPObject* shp = SHPCreateObject(
SHPT_POLYGON, -1, 1, partStart, NULL, 5, xCoords, yCoords, NULL, NULL);
// Write the polygon to the SHP file
if (SHPWriteObject(hSHP, -1, shp) == -1) { // The program crashes here !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
Serial.println("Failed to write SHP object!");
} else {
Serial.println("Polygon written to SHP file.");
}
SHPDestroyObject(shp);
/*
// Write a record to the DBF file
if (!DBFWriteStringAttribute(hDBF, 0, 0, "Example Polygon")) {
Serial.println("Failed to write to DBF!");
} else {
Serial.println("Record written to DBF file.");
}
*/
// Close files
SHPClose(hSHP);
//DBFClose(hDBF);
Serial.println("Files written successfully.");
}
void loop() {}
```
I am creating a port to osgeo shapelib [1, 2]. My port lives here [3]. The library reads and creates shapefiles to extract geographical information (GIS vector layers) such as polygon maps, GPS points, polylines, etc. I modified the library to work with the SD library reading files from the SD card. The reading part works great so far. Maybe it is enough to be able to read with esp32. However, I want to push it a bit forward, and I also want to achieve the writing functionality.
The problem is:
Guru Meditation Error: Core 1 panic'ed (LoadProhibited). Exception was unhandled.
After some debugging, I found out that the problem occurs when a file.write runs with mode "w+b". Particularly here:
if (psSHP->sHooks.FWrite(pabyRec, nRecordSize, 1, psSHP->fpSHP) < 1) // https://github.com/aferust/ShapeLibForE ... .cpp#L1757
which invokes this function:
[https://github.com/aferust/ShapeLibForE ... ks.cpp#L33]
...
SAOffset SADFWrite(const void *p, SAOffset size, SAOffset nmemb, SAFile &file)
{
size_t bytesWritten = file.write((const uint8_t *)p, size * nmemb); // problem here
...
Of course, I checked if there are null or unallocated buffers, but everything is what it is supposed to be. I am stuck in this problem and need help.
Thanks in advance!
1: http://shapelib.maptools.org/
2: https://github.com/OSGeo/shapelib
3: https://github.com/aferust/ShapeLibForESP32
A test code to reproduce the problem:
```
#include "shapefil.hpp"
#include "SD.h"
void setup() {
Serial.begin(115200);
if (!SD.begin()) {
Serial.println("Card Mount Failed");
return;
}
SHPsetFileSystem(SD);
// Open SHP and DBF files for writing
SHPHandle hSHP = SHPCreate("/p1.shp", SHPT_POLYGON);
//DBFHandle hDBF = DBFCreate("/p1.dbf");
if (hSHP == nullptr /*|| hDBF == nullptr*/) {
Serial.println("Failed to create SHP or DBF file!");
return;
}
/*
// Add a field to the DBF file
if (DBFAddField(hDBF, "Name", FTString, 20, 0) == -1) {
Serial.println("Failed to add field to DBF!");
return;
}
*/
// Create a polygon
double xCoords[] = {0.0, 1.0, 1.0, 0.0, 0.0}; // X coordinates
double yCoords[] = {0.0, 0.0, 1.0, 1.0, 0.0}; // Y coordinates
int partStart[] = {0}; // One part starting at index 0
SHPObject* shp = SHPCreateObject(
SHPT_POLYGON, -1, 1, partStart, NULL, 5, xCoords, yCoords, NULL, NULL);
// Write the polygon to the SHP file
if (SHPWriteObject(hSHP, -1, shp) == -1) { // The program crashes here !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
Serial.println("Failed to write SHP object!");
} else {
Serial.println("Polygon written to SHP file.");
}
SHPDestroyObject(shp);
/*
// Write a record to the DBF file
if (!DBFWriteStringAttribute(hDBF, 0, 0, "Example Polygon")) {
Serial.println("Failed to write to DBF!");
} else {
Serial.println("Record written to DBF file.");
}
*/
// Close files
SHPClose(hSHP);
//DBFClose(hDBF);
Serial.println("Files written successfully.");
}
void loop() {}
```