Martijn Braam: 1 Sanitize types 3 files changed, 65 insertions(+), 63 deletions(-)
Most devices are aarch64 which I think use 64-bit longs (though, size isn't really a problem at this scale). https://1nine.com/arms-64-bit-mode-aarch64-armv8/ The number of tfb_ api calls we make far exceeds the number of C api calls, so wouldn't it be neater to use int and only have to cast from long->int a few times, rather than ever time we call some tfblib function?
Copy & paste the following snippet into your terminal to import this patchset into git:
curl -s https://lists.sr.ht/~calebccff/pbsplash/patches/33579/mbox | git am -3Learn more about email & git
Make the types for variables more consistent to limit casts. All physical dimensions are floats and pixel coordinates are long except on the interface with tflib which uses int.
Out of interest, why use long for pixel coordinates instead of int? Do any values get close to exceeding INT_MAX?they don't, but on ARM int and long are both 32 bits. since most C apis dealing with numbers give long as result making all the coordinates consistently long makes most of the code a bit neater. the (int)somelong casts are no-ops on the ARM builds when checking with godbolt.
--- include/pbsplash.h | 2 +- src/animate.c | 30 +++++++++------ src/pbsplash.c | 96 ++++++++++++++++++++++------------------------ 3 files changed, 65 insertions(+), 63 deletions(-) diff --git a/include/pbsplash.h b/include/pbsplash.h index b855f28..423f128 100644 --- a/include/pbsplash.h +++ b/include/pbsplash.h @@ -10,6 +10,6 @@ struct col { }; }; -void animate_frame(int frame, int w, int h, long dpi); +void animate_frame(int frame, long w, long h, float dpi); #endif diff --git a/src/animate.c b/src/animate.c index eb70769..c249ae8 100644 --- a/src/animate.c +++ b/src/animate.c @@ -1,5 +1,4 @@ #include <math.h> -#include <stdio.h> #include <tfblib/tfblib.h> #include <tfblib/tfb_colors.h> #include "pbsplash.h" @@ -12,27 +11,34 @@ struct col color = { .r = 255, .g = 255, .b = 255, .a = 255 }; #define speed 3 -void circles_wave(int frame, int w, int y_off, long dpi) +void circles_wave(int frame, long w, long y_off, float dpi) { unsigned int t_col = tfb_make_color(color.r, color.g, color.b); - int f = frame * speed; + long f = frame * speed; int rad = (int)(dpi * 4 / 96.0); int dist = rad * 4; int amplitude = rad * 2; - int left = (w / 2) - (dist * (n_circles - 1) / 2.0); - for (unsigned int i = 0; i < n_circles; i++) { - int x = left + (i * dist); - double offset = sin(f / 60.0 * PI + i); - int y = y_off + offset * amplitude; - tfb_fill_rect(x - rad - 1, y_off - amplitude - rad, rad * 2 + 2, + long left = (long)(((float)w / 2.f) - + ((float)dist * (n_circles - 1) / 2.0f)); + + for (int i = 0; i < n_circles; i++) { + long x = left + (i * dist); + double offset = sin((double)f / 60.0 * PI + i); + long y = y_off + (long)(offset * amplitude); + + // Clear column for the dot + tfb_fill_rect((int)(x - rad - 1), + (int)(y_off - amplitude - rad), rad * 2 + 2, 400 + rad * 2, tfb_black); - tfb_fill_circle(x, y, rad, t_col); + + // Draw new dot + tfb_fill_circle((int)x, (int)y, rad, t_col); } } -void animate_frame(int frame, int w, int h, long dpi) +void animate_frame(int frame, long w, long h, float dpi) { - circles_wave(frame, w, h * 0.75, dpi); + circles_wave(frame, w, (h * 3) >> 2, dpi); } diff --git a/src/pbsplash.c b/src/pbsplash.c index 074ec40..b36a9b4 100644 --- a/src/pbsplash.c +++ b/src/pbsplash.c @@ -20,7 +20,6 @@ #include "pbsplash.h" -#define MSG_MAX_LEN 4096 #define DEFAULT_FONT_PATH "/usr/share/pbsplash/OpenSans-Regular.svg" #define LOGO_SIZE_MAX_MM 90 #define FONT_SIZE_PT 9 @@ -39,7 +38,7 @@ struct col background_color = { .r = 0, .g = 0, .b = 0, .a = 255 }; #define LOG(fmt, ...) \ do { \ if (debug) \ - printf(fmt, ##__VA_ARGS__); \ + printf(fmt, ##__VA_ARGS__); \ } while (0) int usage() @@ -65,8 +64,8 @@ void term(int signum) terminate = 1; } -static void blit_buf(unsigned char *buf, int x, int y, int w, int h, bool vflip, - bool redraw) +static void blit_buf(const unsigned char *buf, long x, long y, long w, long h, + bool vflip, bool redraw) { struct col prev_col = { .r = 0, .g = 0, .b = 0, .a = 0 }; unsigned int col = tfb_make_color( @@ -76,7 +75,7 @@ static void blit_buf(unsigned char *buf, int x, int y, int w, int h, bool vflip, for (size_t j = 0; j < h; j++) { #if DEBUGRENDER == 1 if (i == 0 || i == w - 1 || j == 0 || j == h - 1) { - tfb_draw_pixel(x + i, y + h - j, tfb_red); + tfb_draw_pixel((int)x + (int)i, (int)y + (int)h - (int)j, tfb_red); continue; } #endif @@ -107,43 +106,42 @@ static void blit_buf(unsigned char *buf, int x, int y, int w, int h, bool vflip, col = tfb_make_color(rgba.r, rgba.g, rgba.b); } if (vflip) - tfb_draw_pixel(x + i, y + h - j, col); + tfb_draw_pixel((int)(x + i), (int)(y + h - j), + col); else - tfb_draw_pixel(x + i, y + j, col); + tfb_draw_pixel((int)(x + i), (int)(y + j), col); } } } -static void draw_svg(NSVGimage *image, int x, int y, int w, int h) +static void draw_svg(NSVGimage *image, long x, long y, long w, long h) { - float sz = (int)((float)w / (float)image->width * 100.f) / 100.f; - LOG("draw_svg: %dx%d, %dx%d, %f\n", x, y, w, h, sz); + float sz = (float)w / image->width; + LOG("draw_svg: %ldx%ld, %ldx%ld, %f\n", x, y, w, h, sz); NSVGrasterizer *rast = nsvgCreateRasterizer(); unsigned char *img = malloc(w * h * 4); - nsvgRasterize(rast, image, 0, 0, sz, img, w, h, w * 4); + nsvgRasterize(rast, image, 0, 0, sz, img, (int)w, (int)h, (int)w * 4); - blit_buf(img, x, y, w, h, false, false); + blit_buf(img, x, y, (int)w, (int)h, false, false); free(img); nsvgDeleteRasterizer(rast); } -static void draw_text(NSVGimage *font, char *text, int x, int y, int width, - int height, float scale, unsigned int tfb_col) +static void draw_text(NSVGimage *font, char *text, long x, long y, long width, + long height, float scale, unsigned int tfb_col) { - LOG("text '%s': fontsz=%f, x=%d, y=%d, dimensions: %d x %d\n", text, + LOG("text '%s': fontsz=%f, x=%ld, y=%ld, dimensions: %ld x %ld\n", text, scale, x, y, width, height); - NSVGshape **shapes = nsvgGetTextShapes(font, text, strlen(text)); unsigned char *img = malloc(width * height * 4); NSVGrasterizer *rast = nsvgCreateRasterizer(); - nsvgRasterizeText(rast, font, 0, 0, scale, img, width, height, - width * 4, text); + nsvgRasterizeText(rast, font, 4, 0, scale, img, (int)width, (int)height, + (int)width * 4, text); blit_buf(img, x, y, width, height, true, false); free(img); - free(shapes); nsvgDeleteRasterizer(rast); } @@ -152,24 +150,20 @@ static void draw_text(NSVGimage *font, char *text, int x, int y, int width, * based on the font size and the font SVG file. */ static void getTextDimensions(NSVGimage *font, char *text, float scale, - int *width, int *height) + float *width, float *height) { - int i = 0; - *width = 0; // The height is simply the height of the font * the scale factor - *height = (font->fontAscent - font->fontDescent) * scale; - if (text == NULL) - return; + *height = (float)(font->fontAscent - font->fontDescent) * scale; - NSVGshape **shapes = nsvgGetTextShapes(font, text, strlen(text)); + NSVGshape **shapes = nsvgGetTextShapes(font, text, (int)strlen(text)); // Iterate over every glyph in the string to get the total width - for (i = 0; i < strlen(text); i++) { + for (int i = 0; i < strlen(text); i++) { NSVGshape *shape = shapes[i]; if (shape) { - *width += (float)shapes[i]->horizAdvX * scale + 0.5; + *width += (float)shapes[i]->horizAdvX * scale + 0.5f; } else { - *width += font->defaultHorizAdv * scale; + *width += (float)font->defaultHorizAdv * scale; } } @@ -188,7 +182,7 @@ int main(int argc, char **argv) struct sigaction action; float font_size = FONT_SIZE_PT; int optflag; - long dpi = 0; + float dpi = 0; memset(active_tty, '\0', TTY_PATH_LEN); strcat(active_tty, "/dev/"); @@ -228,7 +222,7 @@ int main(int argc, char **argv) fprintf(stderr, "--dpi requires an argument\n"); return usage(); } - dpi = strtol(optarg, &end, 10); + dpi = strtof(optarg, &end); if (end == optarg) { fprintf(stderr, "Invalid font size: %s\n", optarg); @@ -242,7 +236,7 @@ int main(int argc, char **argv) { FILE *fp = fopen("/sys/devices/virtual/tty/tty0/active", "r"); - int len = strlen(active_tty); + unsigned long len = strlen(active_tty); char *ptr = active_tty + len; if (fp != NULL) { fgets(ptr, TTY_PATH_LEN - len, fp); @@ -264,17 +258,17 @@ int main(int argc, char **argv) int w = (int)tfb_screen_width(); int h = (int)tfb_screen_height(); - int w_mm = tfb_screen_width_mm(); - int h_mm = tfb_screen_height_mm(); + float w_mm = (float)tfb_screen_width_mm(); + float h_mm = (float)tfb_screen_height_mm(); // If DPI is specified on cmdline then calculate display size from it // otherwise calculate the dpi based on the display size. if (dpi > 0) { - w_mm = w / (float)dpi * 25.4; - h_mm = h / (float)dpi * 25.4; + w_mm = (float)w / dpi * 25.4f; + h_mm = (float)h / dpi * 25.4f; } else { - dpi = (float)w / (float)w_mm * 25.4; + dpi = (float)w / (float)w_mm * 25.4f; } - int pixels_per_milli = (float)w / (float)w_mm; + float pixels_per_milli = (float)w / w_mm; float logo_size_px = (float)(w < h ? w : h) * 0.75f; if (w_mm > 0 && h_mm > 0) { @@ -289,8 +283,8 @@ int main(int argc, char **argv) } } - LOG("%dx%d @ %dx%dmm, dpi=%ld, logo_size_px=%f\n", w, h, w_mm, h_mm, - dpi, logo_size_px); + LOG("%dx%d @ %fx%fmm, dpi=%f, logo_size_px=%f\n", w, h, w_mm, h_mm, dpi, + logo_size_px); image = nsvgParseFromFile(splash_image, "", logo_size_px); if (!image) { @@ -302,8 +296,8 @@ int main(int argc, char **argv) float sz = (float)logo_size_px / (image->width > image->height ? image->width : image->height); - int image_w = image->width * sz + 0.5; - int image_h = image->height * sz + 0.5; + float image_w = image->width * sz; + float image_h = image->height * sz; float x = (float)w / 2; float y = (float)h / 2; // Center the image @@ -313,10 +307,10 @@ int main(int argc, char **argv) tfb_clear_screen(tfb_make_color(background_color.r, background_color.g, background_color.b)); - draw_svg(image, x, y, image_w, image_h); + draw_svg(image, (int)x, (int)y, lroundf(image_w), lroundf(image_h)); if (message) { - int textWidth, textHeight; + float textWidth, textHeight; font = nsvgParseFromFile(font_path, "px", 512); if (!font || !font->shapes) { @@ -326,17 +320,18 @@ int main(int argc, char **argv) } float fontsz = ((float)font_size * PT_TO_MM) / - (font->fontAscent - font->fontDescent) * + (float)(font->fontAscent - font->fontDescent) * pixels_per_milli; getTextDimensions(font, message, fontsz, &textWidth, &textHeight); - int tx = w / 2.f - textWidth / 2.f; - int ty = y + image_h + textHeight * 0.5f + MM_TO_PX(dpi, 2); + int tx = (int)((float)w / 2.f - textWidth / 2.f); + int ty = (int)(y + image_h + textHeight * 0.5f + + MM_TO_PX(dpi, 2)); - draw_text(font, message, tx, ty, textWidth, textHeight, fontsz, - tfb_gray); + draw_text(font, message, tx, ty, lroundf(textWidth), + lroundf(textHeight), fontsz, tfb_gray); } tfb_flush_window(); @@ -352,7 +347,8 @@ int main(int argc, char **argv) // Login started and has reset the TTY back to text mode if (tty_mode == KD_TEXT) { // tfb_flush_window(); - draw_svg(image, x, y, image_w, image_h); + draw_svg(image, (int)x, (int)y, lroundf(image_w), + lroundf(image_h)); goto out; } // usleep(1666); -- 2.36.1