PokittoLib is the library needed for programming the Pokitto DIY game console (www.pokitto.com)

Committer:
spinal
Date:
Sun Nov 18 15:47:54 2018 +0000
Revision:
64:6e6c6c2b664e
Parent:
55:d2eedf44d03b
added fix for directrectangle()

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Pokitto 55:d2eedf44d03b 1 /*
Pokitto 55:d2eedf44d03b 2 Copyright 2001 Georges Menie
Pokitto 55:d2eedf44d03b 3 https://www.menie.org/georges/embedded/small_printf_source_code.html
Pokitto 55:d2eedf44d03b 4
Pokitto 55:d2eedf44d03b 5 This program is free software; you can redistribute it and/or modify
Pokitto 55:d2eedf44d03b 6 it under the terms of the GNU Lesser General Public License as published by
Pokitto 55:d2eedf44d03b 7 the Free Software Foundation; either version 2 of the License, or
Pokitto 55:d2eedf44d03b 8 (at your option) any later version.
Pokitto 55:d2eedf44d03b 9
Pokitto 55:d2eedf44d03b 10 This program is distributed in the hope that it will be useful,
Pokitto 55:d2eedf44d03b 11 but WITHOUT ANY WARRANTY; without even the implied warranty of
Pokitto 55:d2eedf44d03b 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
Pokitto 55:d2eedf44d03b 13 GNU Lesser General Public License for more details.
Pokitto 55:d2eedf44d03b 14
Pokitto 55:d2eedf44d03b 15 You should have received a copy of the GNU Lesser General Public License
Pokitto 55:d2eedf44d03b 16 along with this program; if not, write to the Free Software
Pokitto 55:d2eedf44d03b 17 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Pokitto 55:d2eedf44d03b 18 */
Pokitto 55:d2eedf44d03b 19
Pokitto 55:d2eedf44d03b 20 /*
Pokitto 55:d2eedf44d03b 21 putchar is the only external dependency for this file,
Pokitto 55:d2eedf44d03b 22 if you have a working putchar, just remove the following
Pokitto 55:d2eedf44d03b 23 define. If the function should be called something else,
Pokitto 55:d2eedf44d03b 24 replace outbyte(c) by your own function call.
Pokitto 55:d2eedf44d03b 25 */
Pokitto 55:d2eedf44d03b 26
Pokitto 55:d2eedf44d03b 27 #include "PokittoDisplay.h"
Pokitto 55:d2eedf44d03b 28
Pokitto 55:d2eedf44d03b 29 //#define putchar(c) outbyte(c)
Pokitto 55:d2eedf44d03b 30
Pokitto 55:d2eedf44d03b 31 static void printchar(char **str, int c)
Pokitto 55:d2eedf44d03b 32 {
Pokitto 55:d2eedf44d03b 33 //extern int putchar(int c);
Pokitto 55:d2eedf44d03b 34
Pokitto 55:d2eedf44d03b 35 if (str) {
Pokitto 55:d2eedf44d03b 36 **str = c;
Pokitto 55:d2eedf44d03b 37 ++(*str);
Pokitto 55:d2eedf44d03b 38 }
Pokitto 55:d2eedf44d03b 39 //else (void)putchar(c);
Pokitto 55:d2eedf44d03b 40 else Pokitto::Display::print((const char*)&c);
Pokitto 55:d2eedf44d03b 41 }
Pokitto 55:d2eedf44d03b 42
Pokitto 55:d2eedf44d03b 43 #define PAD_RIGHT 1
Pokitto 55:d2eedf44d03b 44 #define PAD_ZERO 2
Pokitto 55:d2eedf44d03b 45
Pokitto 55:d2eedf44d03b 46 static int prints(char **out, const char *string, int width, int pad)
Pokitto 55:d2eedf44d03b 47 {
Pokitto 55:d2eedf44d03b 48 register int pc = 0, padchar = ' ';
Pokitto 55:d2eedf44d03b 49
Pokitto 55:d2eedf44d03b 50 if (width > 0) {
Pokitto 55:d2eedf44d03b 51 register int len = 0;
Pokitto 55:d2eedf44d03b 52 register const char *ptr;
Pokitto 55:d2eedf44d03b 53 for (ptr = string; *ptr; ++ptr) ++len;
Pokitto 55:d2eedf44d03b 54 if (len >= width) width = 0;
Pokitto 55:d2eedf44d03b 55 else width -= len;
Pokitto 55:d2eedf44d03b 56 if (pad & PAD_ZERO) padchar = '0';
Pokitto 55:d2eedf44d03b 57 }
Pokitto 55:d2eedf44d03b 58 if (!(pad & PAD_RIGHT)) {
Pokitto 55:d2eedf44d03b 59 for ( ; width > 0; --width) {
Pokitto 55:d2eedf44d03b 60 printchar (out, padchar);
Pokitto 55:d2eedf44d03b 61 ++pc;
Pokitto 55:d2eedf44d03b 62 }
Pokitto 55:d2eedf44d03b 63 }
Pokitto 55:d2eedf44d03b 64 for ( ; *string ; ++string) {
Pokitto 55:d2eedf44d03b 65 printchar (out, *string);
Pokitto 55:d2eedf44d03b 66 ++pc;
Pokitto 55:d2eedf44d03b 67 }
Pokitto 55:d2eedf44d03b 68 for ( ; width > 0; --width) {
Pokitto 55:d2eedf44d03b 69 printchar (out, padchar);
Pokitto 55:d2eedf44d03b 70 ++pc;
Pokitto 55:d2eedf44d03b 71 }
Pokitto 55:d2eedf44d03b 72
Pokitto 55:d2eedf44d03b 73 return pc;
Pokitto 55:d2eedf44d03b 74 }
Pokitto 55:d2eedf44d03b 75
Pokitto 55:d2eedf44d03b 76 /* the following should be enough for 32 bit int */
Pokitto 55:d2eedf44d03b 77 #define PRINT_BUF_LEN 12
Pokitto 55:d2eedf44d03b 78
Pokitto 55:d2eedf44d03b 79 static int printi(char **out, int i, int b, int sg, int width, int pad, int letbase)
Pokitto 55:d2eedf44d03b 80 {
Pokitto 55:d2eedf44d03b 81 char print_buf[PRINT_BUF_LEN];
Pokitto 55:d2eedf44d03b 82 register char *s;
Pokitto 55:d2eedf44d03b 83 register int t, neg = 0, pc = 0;
Pokitto 55:d2eedf44d03b 84 register unsigned int u = i;
Pokitto 55:d2eedf44d03b 85
Pokitto 55:d2eedf44d03b 86 if (i == 0) {
Pokitto 55:d2eedf44d03b 87 print_buf[0] = '0';
Pokitto 55:d2eedf44d03b 88 print_buf[1] = '\0';
Pokitto 55:d2eedf44d03b 89 return prints (out, print_buf, width, pad);
Pokitto 55:d2eedf44d03b 90 }
Pokitto 55:d2eedf44d03b 91
Pokitto 55:d2eedf44d03b 92 if (sg && b == 10 && i < 0) {
Pokitto 55:d2eedf44d03b 93 neg = 1;
Pokitto 55:d2eedf44d03b 94 u = -i;
Pokitto 55:d2eedf44d03b 95 }
Pokitto 55:d2eedf44d03b 96
Pokitto 55:d2eedf44d03b 97 s = print_buf + PRINT_BUF_LEN-1;
Pokitto 55:d2eedf44d03b 98 *s = '\0';
Pokitto 55:d2eedf44d03b 99
Pokitto 55:d2eedf44d03b 100 while (u) {
Pokitto 55:d2eedf44d03b 101 t = u % b;
Pokitto 55:d2eedf44d03b 102 if( t >= 10 )
Pokitto 55:d2eedf44d03b 103 t += letbase - '0' - 10;
Pokitto 55:d2eedf44d03b 104 *--s = t + '0';
Pokitto 55:d2eedf44d03b 105 u /= b;
Pokitto 55:d2eedf44d03b 106 }
Pokitto 55:d2eedf44d03b 107
Pokitto 55:d2eedf44d03b 108 if (neg) {
Pokitto 55:d2eedf44d03b 109 if( width && (pad & PAD_ZERO) ) {
Pokitto 55:d2eedf44d03b 110 printchar (out, '-');
Pokitto 55:d2eedf44d03b 111 ++pc;
Pokitto 55:d2eedf44d03b 112 --width;
Pokitto 55:d2eedf44d03b 113 }
Pokitto 55:d2eedf44d03b 114 else {
Pokitto 55:d2eedf44d03b 115 *--s = '-';
Pokitto 55:d2eedf44d03b 116 }
Pokitto 55:d2eedf44d03b 117 }
Pokitto 55:d2eedf44d03b 118
Pokitto 55:d2eedf44d03b 119 return pc + prints (out, s, width, pad);
Pokitto 55:d2eedf44d03b 120 }
Pokitto 55:d2eedf44d03b 121
Pokitto 55:d2eedf44d03b 122 static int _ext_print(char **out, int *varg)
Pokitto 55:d2eedf44d03b 123 {
Pokitto 55:d2eedf44d03b 124 register int width, pad;
Pokitto 55:d2eedf44d03b 125 register int pc = 0;
Pokitto 55:d2eedf44d03b 126 register char *format = (char *)(*varg++);
Pokitto 55:d2eedf44d03b 127 char scr[2];
Pokitto 55:d2eedf44d03b 128
Pokitto 55:d2eedf44d03b 129 for (; *format != 0; ++format) {
Pokitto 55:d2eedf44d03b 130 if (*format == '%') {
Pokitto 55:d2eedf44d03b 131 ++format;
Pokitto 55:d2eedf44d03b 132 width = pad = 0;
Pokitto 55:d2eedf44d03b 133 if (*format == '\0') break;
Pokitto 55:d2eedf44d03b 134 if (*format == '%') goto out;
Pokitto 55:d2eedf44d03b 135 if (*format == '-') {
Pokitto 55:d2eedf44d03b 136 ++format;
Pokitto 55:d2eedf44d03b 137 pad = PAD_RIGHT;
Pokitto 55:d2eedf44d03b 138 }
Pokitto 55:d2eedf44d03b 139 while (*format == '0') {
Pokitto 55:d2eedf44d03b 140 ++format;
Pokitto 55:d2eedf44d03b 141 pad |= PAD_ZERO;
Pokitto 55:d2eedf44d03b 142 }
Pokitto 55:d2eedf44d03b 143 for ( ; *format >= '0' && *format <= '9'; ++format) {
Pokitto 55:d2eedf44d03b 144 width *= 10;
Pokitto 55:d2eedf44d03b 145 width += *format - '0';
Pokitto 55:d2eedf44d03b 146 }
Pokitto 55:d2eedf44d03b 147 if( *format == 's' ) {
Pokitto 55:d2eedf44d03b 148 register char *s = *((char **)varg++);
Pokitto 55:d2eedf44d03b 149 pc += prints (out, s?s:"(null)", width, pad);
Pokitto 55:d2eedf44d03b 150 continue;
Pokitto 55:d2eedf44d03b 151 }
Pokitto 55:d2eedf44d03b 152 if( *format == 'd' ) {
Pokitto 55:d2eedf44d03b 153 pc += printi (out, *varg++, 10, 1, width, pad, 'a');
Pokitto 55:d2eedf44d03b 154 continue;
Pokitto 55:d2eedf44d03b 155 }
Pokitto 55:d2eedf44d03b 156 if( *format == 'x' ) {
Pokitto 55:d2eedf44d03b 157 pc += printi (out, *varg++, 16, 0, width, pad, 'a');
Pokitto 55:d2eedf44d03b 158 continue;
Pokitto 55:d2eedf44d03b 159 }
Pokitto 55:d2eedf44d03b 160 if( *format == 'X' ) {
Pokitto 55:d2eedf44d03b 161 pc += printi (out, *varg++, 16, 0, width, pad, 'A');
Pokitto 55:d2eedf44d03b 162 continue;
Pokitto 55:d2eedf44d03b 163 }
Pokitto 55:d2eedf44d03b 164 if( *format == 'u' ) {
Pokitto 55:d2eedf44d03b 165 pc += printi (out, *varg++, 10, 0, width, pad, 'a');
Pokitto 55:d2eedf44d03b 166 continue;
Pokitto 55:d2eedf44d03b 167 }
Pokitto 55:d2eedf44d03b 168 if( *format == 'c' ) {
Pokitto 55:d2eedf44d03b 169 /* char are converted to int then pushed on the stack */
Pokitto 55:d2eedf44d03b 170 scr[0] = *varg++;
Pokitto 55:d2eedf44d03b 171 scr[1] = '\0';
Pokitto 55:d2eedf44d03b 172 pc += prints (out, scr, width, pad);
Pokitto 55:d2eedf44d03b 173 continue;
Pokitto 55:d2eedf44d03b 174 }
Pokitto 55:d2eedf44d03b 175 }
Pokitto 55:d2eedf44d03b 176 else {
Pokitto 55:d2eedf44d03b 177 out:
Pokitto 55:d2eedf44d03b 178 printchar (out, *format);
Pokitto 55:d2eedf44d03b 179 ++pc;
Pokitto 55:d2eedf44d03b 180 }
Pokitto 55:d2eedf44d03b 181 }
Pokitto 55:d2eedf44d03b 182 if (out) **out = '\0';
Pokitto 55:d2eedf44d03b 183 return pc;
Pokitto 55:d2eedf44d03b 184 }
Pokitto 55:d2eedf44d03b 185
Pokitto 55:d2eedf44d03b 186 /* assuming sizeof(void *) == sizeof(int) */
Pokitto 55:d2eedf44d03b 187
Pokitto 55:d2eedf44d03b 188 int _ext_printf(const char *format, ...)
Pokitto 55:d2eedf44d03b 189 {
Pokitto 55:d2eedf44d03b 190 register int *varg = (int *)(&format);
Pokitto 55:d2eedf44d03b 191 return _ext_print(0, varg);
Pokitto 55:d2eedf44d03b 192 }
Pokitto 55:d2eedf44d03b 193
Pokitto 55:d2eedf44d03b 194 int _ext_sprintf(char *out, const char *format, ...)
Pokitto 55:d2eedf44d03b 195 {
Pokitto 55:d2eedf44d03b 196 register int *varg = (int *)(&format);
Pokitto 55:d2eedf44d03b 197 return _ext_print(&out, varg);
Pokitto 55:d2eedf44d03b 198 }
Pokitto 55:d2eedf44d03b 199
Pokitto 55:d2eedf44d03b 200 /**
Pokitto 55:d2eedf44d03b 201 * Use an external (PokittoPrintf.cpp) small implementation of printf
Pokitto 55:d2eedf44d03b 202 * to simplify printing formatted strings
Pokitto 55:d2eedf44d03b 203 * @param pointer to const formatted string
Pokitto 55:d2eedf44d03b 204 */
Pokitto 55:d2eedf44d03b 205
Pokitto 55:d2eedf44d03b 206 int Pokitto::Display::printf(const char *format, ...) {
Pokitto 55:d2eedf44d03b 207 register int *varg = (int *)(&format);
Pokitto 55:d2eedf44d03b 208 return _ext_print(0, varg);
Pokitto 55:d2eedf44d03b 209 };
Pokitto 55:d2eedf44d03b 210
Pokitto 55:d2eedf44d03b 211 // The following is from the original source and is left here for reference and LGPL
Pokitto 55:d2eedf44d03b 212 // source: https://www.menie.org/georges/embedded/small_printf_source_code.html
Pokitto 55:d2eedf44d03b 213
Pokitto 55:d2eedf44d03b 214 #ifdef TEST_PRINTF
Pokitto 55:d2eedf44d03b 215 int main(void)
Pokitto 55:d2eedf44d03b 216 {
Pokitto 55:d2eedf44d03b 217 char *ptr = "Hello world!";
Pokitto 55:d2eedf44d03b 218 char *np = 0;
Pokitto 55:d2eedf44d03b 219 int i = 5;
Pokitto 55:d2eedf44d03b 220 unsigned int bs = sizeof(int)*8;
Pokitto 55:d2eedf44d03b 221 int mi;
Pokitto 55:d2eedf44d03b 222 char buf[80];
Pokitto 55:d2eedf44d03b 223
Pokitto 55:d2eedf44d03b 224 mi = (1 << (bs-1)) + 1;
Pokitto 55:d2eedf44d03b 225 printf("%s\n", ptr);
Pokitto 55:d2eedf44d03b 226 printf("printf test\n");
Pokitto 55:d2eedf44d03b 227 printf("%s is null pointer\n", np);
Pokitto 55:d2eedf44d03b 228 printf("%d = 5\n", i);
Pokitto 55:d2eedf44d03b 229 printf("%d = - max int\n", mi);
Pokitto 55:d2eedf44d03b 230 printf("char %c = 'a'\n", 'a');
Pokitto 55:d2eedf44d03b 231 printf("hex %x = ff\n", 0xff);
Pokitto 55:d2eedf44d03b 232 printf("hex %02x = 00\n", 0);
Pokitto 55:d2eedf44d03b 233 printf("signed %d = unsigned %u = hex %x\n", -3, -3, -3);
Pokitto 55:d2eedf44d03b 234 printf("%d %s(s)%", 0, "message");
Pokitto 55:d2eedf44d03b 235 printf("\n");
Pokitto 55:d2eedf44d03b 236 printf("%d %s(s) with %%\n", 0, "message");
Pokitto 55:d2eedf44d03b 237 sprintf(buf, "justif: \"%-10s\"\n", "left"); printf("%s", buf);
Pokitto 55:d2eedf44d03b 238 sprintf(buf, "justif: \"%10s\"\n", "right"); printf("%s", buf);
Pokitto 55:d2eedf44d03b 239 sprintf(buf, " 3: %04d zero padded\n", 3); printf("%s", buf);
Pokitto 55:d2eedf44d03b 240 sprintf(buf, " 3: %-4d left justif.\n", 3); printf("%s", buf);
Pokitto 55:d2eedf44d03b 241 sprintf(buf, " 3: %4d right justif.\n", 3); printf("%s", buf);
Pokitto 55:d2eedf44d03b 242 sprintf(buf, "-3: %04d zero padded\n", -3); printf("%s", buf);
Pokitto 55:d2eedf44d03b 243 sprintf(buf, "-3: %-4d left justif.\n", -3); printf("%s", buf);
Pokitto 55:d2eedf44d03b 244 sprintf(buf, "-3: %4d right justif.\n", -3); printf("%s", buf);
Pokitto 55:d2eedf44d03b 245
Pokitto 55:d2eedf44d03b 246 return 0;
Pokitto 55:d2eedf44d03b 247 }
Pokitto 55:d2eedf44d03b 248
Pokitto 55:d2eedf44d03b 249 /*
Pokitto 55:d2eedf44d03b 250 * if you compile this file with
Pokitto 55:d2eedf44d03b 251 * gcc -Wall $(YOUR_C_OPTIONS) -DTEST_PRINTF -c printf.c
Pokitto 55:d2eedf44d03b 252 * you will get a normal warning:
Pokitto 55:d2eedf44d03b 253 * printf.c:214: warning: spurious trailing `%' in format
Pokitto 55:d2eedf44d03b 254 * this line is testing an invalid % at the end of the format string.
Pokitto 55:d2eedf44d03b 255 *
Pokitto 55:d2eedf44d03b 256 * this should display (on 32bit int machine) :
Pokitto 55:d2eedf44d03b 257 *
Pokitto 55:d2eedf44d03b 258 * Hello world!
Pokitto 55:d2eedf44d03b 259 * printf test
Pokitto 55:d2eedf44d03b 260 * (null) is null pointer
Pokitto 55:d2eedf44d03b 261 * 5 = 5
Pokitto 55:d2eedf44d03b 262 * -2147483647 = - max int
Pokitto 55:d2eedf44d03b 263 * char a = 'a'
Pokitto 55:d2eedf44d03b 264 * hex ff = ff
Pokitto 55:d2eedf44d03b 265 * hex 00 = 00
Pokitto 55:d2eedf44d03b 266 * signed -3 = unsigned 4294967293 = hex fffffffd
Pokitto 55:d2eedf44d03b 267 * 0 message(s)
Pokitto 55:d2eedf44d03b 268 * 0 message(s) with %
Pokitto 55:d2eedf44d03b 269 * justif: "left "
Pokitto 55:d2eedf44d03b 270 * justif: " right"
Pokitto 55:d2eedf44d03b 271 * 3: 0003 zero padded
Pokitto 55:d2eedf44d03b 272 * 3: 3 left justif.
Pokitto 55:d2eedf44d03b 273 * 3: 3 right justif.
Pokitto 55:d2eedf44d03b 274 * -3: -003 zero padded
Pokitto 55:d2eedf44d03b 275 * -3: -3 left justif.
Pokitto 55:d2eedf44d03b 276 * -3: -3 right justif.
Pokitto 55:d2eedf44d03b 277 */
Pokitto 55:d2eedf44d03b 278
Pokitto 55:d2eedf44d03b 279 #endif
Pokitto 55:d2eedf44d03b 280