diff options
Diffstat (limited to 'firmware/drivers/lcd-h100.c')
-rw-r--r-- | firmware/drivers/lcd-h100.c | 39 |
1 files changed, 26 insertions, 13 deletions
diff --git a/firmware/drivers/lcd-h100.c b/firmware/drivers/lcd-h100.c index 42bf13a888..f460165534 100644 --- a/firmware/drivers/lcd-h100.c +++ b/firmware/drivers/lcd-h100.c | |||
@@ -397,24 +397,29 @@ static void bgblock(unsigned char *address, unsigned mask, unsigned bits) | |||
397 | ICODE_ATTR; | 397 | ICODE_ATTR; |
398 | static void bgblock(unsigned char *address, unsigned mask, unsigned bits) | 398 | static void bgblock(unsigned char *address, unsigned mask, unsigned bits) |
399 | { | 399 | { |
400 | mask &= ~bits; | 400 | unsigned data = *address; |
401 | *address = (*address & ~mask) | (bg_pattern & mask); | 401 | |
402 | *address = data ^ ((data ^ bg_pattern) & mask & ~bits); | ||
402 | } | 403 | } |
403 | 404 | ||
404 | static void fgblock(unsigned char *address, unsigned mask, unsigned bits) | 405 | static void fgblock(unsigned char *address, unsigned mask, unsigned bits) |
405 | ICODE_ATTR; | 406 | ICODE_ATTR; |
406 | static void fgblock(unsigned char *address, unsigned mask, unsigned bits) | 407 | static void fgblock(unsigned char *address, unsigned mask, unsigned bits) |
407 | { | 408 | { |
408 | mask &= bits; | 409 | unsigned data = *address; |
409 | *address = (*address & ~mask) | (fg_pattern & mask); | 410 | |
411 | *address = data ^ ((data ^ fg_pattern) & mask & bits); | ||
410 | } | 412 | } |
411 | 413 | ||
412 | static void solidblock(unsigned char *address, unsigned mask, unsigned bits) | 414 | static void solidblock(unsigned char *address, unsigned mask, unsigned bits) |
413 | ICODE_ATTR; | 415 | ICODE_ATTR; |
414 | static void solidblock(unsigned char *address, unsigned mask, unsigned bits) | 416 | static void solidblock(unsigned char *address, unsigned mask, unsigned bits) |
415 | { | 417 | { |
416 | *address = (*address & ~mask) | (bits & mask & fg_pattern) | 418 | unsigned data = *address; |
417 | | (~bits & mask & bg_pattern); | 419 | unsigned bgp = bg_pattern; |
420 | |||
421 | bits = bgp ^ ((bgp ^ fg_pattern) & bits); | ||
422 | *address = data ^ ((data ^ bits) & mask); | ||
418 | } | 423 | } |
419 | 424 | ||
420 | static void flipinvblock(unsigned char *address, unsigned mask, unsigned bits) | 425 | static void flipinvblock(unsigned char *address, unsigned mask, unsigned bits) |
@@ -428,24 +433,29 @@ static void bginvblock(unsigned char *address, unsigned mask, unsigned bits) | |||
428 | ICODE_ATTR; | 433 | ICODE_ATTR; |
429 | static void bginvblock(unsigned char *address, unsigned mask, unsigned bits) | 434 | static void bginvblock(unsigned char *address, unsigned mask, unsigned bits) |
430 | { | 435 | { |
431 | mask &= bits; | 436 | unsigned data = *address; |
432 | *address = (*address & ~mask) | (bg_pattern & mask); | 437 | |
438 | *address = data ^ ((data ^ bg_pattern) & mask & bits); | ||
433 | } | 439 | } |
434 | 440 | ||
435 | static void fginvblock(unsigned char *address, unsigned mask, unsigned bits) | 441 | static void fginvblock(unsigned char *address, unsigned mask, unsigned bits) |
436 | ICODE_ATTR; | 442 | ICODE_ATTR; |
437 | static void fginvblock(unsigned char *address, unsigned mask, unsigned bits) | 443 | static void fginvblock(unsigned char *address, unsigned mask, unsigned bits) |
438 | { | 444 | { |
439 | mask &= ~bits; | 445 | unsigned data = *address; |
440 | *address = (*address & ~mask) | (fg_pattern & mask); | 446 | |
447 | *address = data ^ ((data ^ fg_pattern) & mask & ~bits); | ||
441 | } | 448 | } |
442 | 449 | ||
443 | static void solidinvblock(unsigned char *address, unsigned mask, unsigned bits) | 450 | static void solidinvblock(unsigned char *address, unsigned mask, unsigned bits) |
444 | ICODE_ATTR; | 451 | ICODE_ATTR; |
445 | static void solidinvblock(unsigned char *address, unsigned mask, unsigned bits) | 452 | static void solidinvblock(unsigned char *address, unsigned mask, unsigned bits) |
446 | { | 453 | { |
447 | *address = (*address & ~mask) | (~bits & mask & fg_pattern) | 454 | unsigned data = *address; |
448 | | (bits & mask & bg_pattern); | 455 | unsigned fgp = fg_pattern; |
456 | |||
457 | bits = fgp ^ ((fgp ^ bg_pattern) & bits); | ||
458 | *address = data ^ ((data ^ bits) & mask); | ||
449 | } | 459 | } |
450 | 460 | ||
451 | lcd_blockfunc_type* const lcd_blockfuncs[8] = { | 461 | lcd_blockfunc_type* const lcd_blockfuncs[8] = { |
@@ -455,7 +465,10 @@ lcd_blockfunc_type* const lcd_blockfuncs[8] = { | |||
455 | 465 | ||
456 | static inline void setblock(unsigned char *address, unsigned mask, unsigned bits) | 466 | static inline void setblock(unsigned char *address, unsigned mask, unsigned bits) |
457 | { | 467 | { |
458 | *address = (*address & ~mask) | (bits & mask); | 468 | unsigned data = *address; |
469 | |||
470 | bits ^= data; | ||
471 | *address = data ^ (bits & mask); | ||
459 | } | 472 | } |
460 | 473 | ||
461 | /*** drawing functions ***/ | 474 | /*** drawing functions ***/ |