Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

replace faulty n_ftoa.c implementation that truncated doubles upon co… #16

Merged
merged 5 commits into from
Dec 14, 2021

Conversation

rayozzie
Copy link
Collaborator

For historical reasons (trying to get it to work in extremely low memory on a 16-bit MCU) I had an awful implementation of the JNtoA() function. This replaces it with a better implementation, tested against a golang equivalent and tested with the Arduino program below.

(In case you're wondering, we can't just use snprintf to do the conversions because most microcontroller libraries, including newlib, omit floating point support by default for memory reasons.)

test.ino

#include <Notecard.h>
#include <Wire.h>

#ifdef NOTE_FLOAT
#error "we're not even using double on this platform"
#endif

#define serialNotecard Serial1
#define serialDebugOut Serial
Notecard notecard;

void test(JNUMBER f)
{
	float g;
	char buf1[64], buf2[64];
	JNtoA(f, buf1, -1);
	g = JAtoN(buf1, NULL);
	JNtoA(g, buf2, -1);
	if (strcmp(buf1, buf2) != 0) {
		printf("%s %s", buf1, buf2);
	}
    J *req = JCreateObject();
	if (req == NULL) {
		printf(" REQ-ERROR\n");
	} else {
		JAddNumberToObject(req, "test", f);
		char *reqJSON = JPrintUnformatted(req);
		JDelete(req);
		if (reqJSON == NULL) {
			printf(" PRINT-ERROR\n");
		} else {
			printf(" %s", reqJSON);
			JFree(reqJSON);
		}
	}
	printf("\n");

}

void setup()
{
    delay(2500);
    serialDebugOut.begin(115200);
    notecard.setDebugOutputStream(serialDebugOut);
    notecard.begin(serialNotecard, 9600);

	int limit = 28;
	double f = 1.0;

	printf("sizeof(double) == %d\n", sizeof(f));

	// Test numbers that can be represented in floats, high-to-small
	for (int i = 0; i < limit; i++) {
		test(f);
		f = f / 2;
	}
	// Test numbers that can be represented in floats, small-to-high
	for (int i = 0; i < limit; i++) {
		f = f * 2;
		test(f);
	}
	// Test numbers that can be represented in floats, higher than zero
	for (int i = 0; i < limit*2; i++) {
		f = f * 2;
		test(f);
	}

}

void loop()
{
}

@zfields zfields merged commit 89923aa into master Dec 14, 2021
@zfields zfields deleted the ray-ftoa branch December 14, 2021 22:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants