1 /* $OpenBSD: rasops24.c,v 1.7 2008/06/26 05:42:18 ray Exp $ */ 2 /* $NetBSD: rasops24.c,v 1.12 2000/04/12 14:22:29 pk Exp $ */ 3 4 /*- 5 * Copyright (c) 1999 The NetBSD Foundation, Inc. 6 * All rights reserved. 7 * 8 * This code is derived from software contributed to The NetBSD Foundation 9 * by Andrew Doran. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 20 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 21 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 22 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 23 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 24 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 25 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 26 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 27 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 28 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 29 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 30 * POSSIBILITY OF SUCH DAMAGE. 31 */ 32 33 #include <sys/param.h> 34 #include <sys/systm.h> 35 #include <sys/time.h> 36 37 #include <machine/endian.h> 38 39 #include <dev/wscons/wsdisplayvar.h> 40 #include <dev/wscons/wsconsio.h> 41 #include <dev/rasops/rasops.h> 42 43 void rasops24_erasecols(void *, int, int, int, long); 44 void rasops24_eraserows(void *, int, int, long); 45 void rasops24_putchar(void *, int, int, u_int, long attr); 46 #ifndef RASOPS_SMALL 47 void rasops24_putchar8(void *, int, int, u_int, long attr); 48 void rasops24_putchar12(void *, int, int, u_int, long attr); 49 void rasops24_putchar16(void *, int, int, u_int, long attr); 50 void rasops24_makestamp(struct rasops_info *, long); 51 52 /* 53 * 4x1 stamp for optimized character blitting 54 */ 55 static int32_t stamp[64]; 56 static long stamp_attr; 57 static int stamp_mutex; /* XXX see note in readme */ 58 #endif 59 60 /* 61 * XXX this confuses the hell out of gcc2 (not egcs) which always insists 62 * that the shift count is negative. 63 * 64 * offset = STAMP_SHIFT(fontbits, nibble #) & STAMP_MASK 65 * destination int32_t[0] = STAMP_READ(offset) 66 * destination int32_t[1] = STAMP_READ(offset + 4) 67 * destination int32_t[2] = STAMP_READ(offset + 8) 68 */ 69 #define STAMP_SHIFT(fb,n) ((n*4-4) >= 0 ? (fb)>>(n*4-4):(fb)<<-(n*4-4)) 70 #define STAMP_MASK (0xf << 4) 71 #define STAMP_READ(o) (*(int32_t *)((caddr_t)stamp + (o))) 72 73 /* 74 * Initialize rasops_info struct for this colordepth. 75 */ 76 void 77 rasops24_init(ri) 78 struct rasops_info *ri; 79 { 80 81 switch (ri->ri_font->fontwidth) { 82 #ifndef RASOPS_SMALL 83 case 8: 84 ri->ri_ops.putchar = rasops24_putchar8; 85 break; 86 case 12: 87 ri->ri_ops.putchar = rasops24_putchar12; 88 break; 89 case 16: 90 ri->ri_ops.putchar = rasops24_putchar16; 91 break; 92 #endif 93 default: 94 ri->ri_ops.putchar = rasops24_putchar; 95 break; 96 } 97 98 if (ri->ri_rnum == 0) { 99 ri->ri_rnum = 8; 100 ri->ri_rpos = 0; 101 ri->ri_gnum = 8; 102 ri->ri_gpos = 8; 103 ri->ri_bnum = 8; 104 ri->ri_bpos = 16; 105 } 106 107 ri->ri_ops.erasecols = rasops24_erasecols; 108 ri->ri_ops.eraserows = rasops24_eraserows; 109 } 110 111 /* 112 * Put a single character. This is the generic version. 113 * XXX this bites - we should use masks. 114 */ 115 void 116 rasops24_putchar(cookie, row, col, uc, attr) 117 void *cookie; 118 int row, col; 119 u_int uc; 120 long attr; 121 { 122 int fb, width, height, cnt, clr[2]; 123 struct rasops_info *ri; 124 u_char *dp, *rp, *fr; 125 126 ri = (struct rasops_info *)cookie; 127 128 #ifdef RASOPS_CLIPPING 129 /* Catches 'row < 0' case too */ 130 if ((unsigned)row >= (unsigned)ri->ri_rows) 131 return; 132 133 if ((unsigned)col >= (unsigned)ri->ri_cols) 134 return; 135 #endif 136 137 rp = ri->ri_bits + row * ri->ri_yscale + col * ri->ri_xscale; 138 height = ri->ri_font->fontheight; 139 width = ri->ri_font->fontwidth; 140 141 clr[1] = ri->ri_devcmap[((u_int)attr >> 24) & 0xf]; 142 clr[0] = ri->ri_devcmap[((u_int)attr >> 16) & 0xf]; 143 144 if (uc == ' ') { 145 while (height--) { 146 dp = rp; 147 rp += ri->ri_stride; 148 149 for (cnt = width; cnt; cnt--) { 150 *dp++ = clr[0] >> 16; 151 *dp++ = clr[0] >> 8; 152 *dp++ = clr[0]; 153 } 154 } 155 } else { 156 uc -= ri->ri_font->firstchar; 157 fr = (u_char *)ri->ri_font->data + uc * ri->ri_fontscale; 158 159 while (height--) { 160 dp = rp; 161 fb = fr[3] | (fr[2] << 8) | (fr[1] << 16) | 162 (fr[0] << 24); 163 fr += ri->ri_font->stride; 164 rp += ri->ri_stride; 165 166 for (cnt = width; cnt; cnt--, fb <<= 1) { 167 if ((fb >> 31) & 1) { 168 *dp++ = clr[1] >> 16; 169 *dp++ = clr[1] >> 8; 170 *dp++ = clr[1]; 171 } else { 172 *dp++ = clr[0] >> 16; 173 *dp++ = clr[0] >> 8; 174 *dp++ = clr[0]; 175 } 176 } 177 } 178 } 179 180 /* Do underline */ 181 if ((attr & 1) != 0) { 182 rp -= ri->ri_stride << 1; 183 184 while (width--) { 185 *rp++ = clr[1] >> 16; 186 *rp++ = clr[1] >> 8; 187 *rp++ = clr[1]; 188 } 189 } 190 } 191 192 #ifndef RASOPS_SMALL 193 /* 194 * Recompute the blitting stamp. 195 */ 196 void 197 rasops24_makestamp(ri, attr) 198 struct rasops_info *ri; 199 long attr; 200 { 201 u_int fg, bg, c1, c2, c3, c4; 202 int i; 203 204 fg = ri->ri_devcmap[((u_int)attr >> 24) & 0xf] & 0xffffff; 205 bg = ri->ri_devcmap[((u_int)attr >> 16) & 0xf] & 0xffffff; 206 stamp_attr = attr; 207 208 for (i = 0; i < 64; i += 4) { 209 #if BYTE_ORDER == LITTLE_ENDIAN 210 c1 = (i & 32 ? fg : bg); 211 c2 = (i & 16 ? fg : bg); 212 c3 = (i & 8 ? fg : bg); 213 c4 = (i & 4 ? fg : bg); 214 #else 215 c1 = (i & 8 ? fg : bg); 216 c2 = (i & 4 ? fg : bg); 217 c3 = (i & 16 ? fg : bg); 218 c4 = (i & 32 ? fg : bg); 219 #endif 220 stamp[i+0] = (c1 << 8) | (c2 >> 16); 221 stamp[i+1] = (c2 << 16) | (c3 >> 8); 222 stamp[i+2] = (c3 << 24) | c4; 223 224 #if BYTE_ORDER == LITTLE_ENDIAN 225 if ((ri->ri_flg & RI_BSWAP) == 0) { 226 #else 227 if ((ri->ri_flg & RI_BSWAP) != 0) { 228 #endif 229 stamp[i+0] = swap32(stamp[i+0]); 230 stamp[i+1] = swap32(stamp[i+1]); 231 stamp[i+2] = swap32(stamp[i+2]); 232 } 233 } 234 } 235 236 /* 237 * Put a single character. This is for 8-pixel wide fonts. 238 */ 239 void 240 rasops24_putchar8(cookie, row, col, uc, attr) 241 void *cookie; 242 int row, col; 243 u_int uc; 244 long attr; 245 { 246 struct rasops_info *ri; 247 int height, so, fs; 248 int32_t *rp; 249 u_char *fr; 250 251 /* Can't risk remaking the stamp if it's already in use */ 252 if (stamp_mutex++) { 253 stamp_mutex--; 254 rasops24_putchar(cookie, row, col, uc, attr); 255 return; 256 } 257 258 ri = (struct rasops_info *)cookie; 259 260 #ifdef RASOPS_CLIPPING 261 if ((unsigned)row >= (unsigned)ri->ri_rows) { 262 stamp_mutex--; 263 return; 264 } 265 266 if ((unsigned)col >= (unsigned)ri->ri_cols) { 267 stamp_mutex--; 268 return; 269 } 270 #endif 271 272 /* Recompute stamp? */ 273 if (attr != stamp_attr) 274 rasops24_makestamp(ri, attr); 275 276 rp = (int32_t *)(ri->ri_bits + row*ri->ri_yscale + col*ri->ri_xscale); 277 height = ri->ri_font->fontheight; 278 279 if (uc == (u_int)-1) { 280 int32_t c = stamp[0]; 281 while (height--) { 282 rp[0] = rp[1] = rp[2] = rp[3] = rp[4] = rp[5] = c; 283 DELTA(rp, ri->ri_stride, int32_t *); 284 } 285 } else { 286 uc -= ri->ri_font->firstchar; 287 fr = (u_char *)ri->ri_font->data + uc*ri->ri_fontscale; 288 fs = ri->ri_font->stride; 289 290 while (height--) { 291 so = STAMP_SHIFT(fr[0], 1) & STAMP_MASK; 292 rp[0] = STAMP_READ(so); 293 rp[1] = STAMP_READ(so + 4); 294 rp[2] = STAMP_READ(so + 8); 295 296 so = STAMP_SHIFT(fr[0], 0) & STAMP_MASK; 297 rp[3] = STAMP_READ(so); 298 rp[4] = STAMP_READ(so + 4); 299 rp[5] = STAMP_READ(so + 8); 300 301 fr += fs; 302 DELTA(rp, ri->ri_stride, int32_t *); 303 } 304 } 305 306 /* Do underline */ 307 if ((attr & 1) != 0) { 308 int32_t c = STAMP_READ(52); 309 310 DELTA(rp, -(ri->ri_stride << 1), int32_t *); 311 rp[0] = rp[1] = rp[2] = rp[3] = rp[4] = rp[5] = c; 312 } 313 314 stamp_mutex--; 315 } 316 317 /* 318 * Put a single character. This is for 12-pixel wide fonts. 319 */ 320 void 321 rasops24_putchar12(cookie, row, col, uc, attr) 322 void *cookie; 323 int row, col; 324 u_int uc; 325 long attr; 326 { 327 struct rasops_info *ri; 328 int height, so, fs; 329 int32_t *rp; 330 u_char *fr; 331 332 /* Can't risk remaking the stamp if it's already in use */ 333 if (stamp_mutex++) { 334 stamp_mutex--; 335 rasops24_putchar(cookie, row, col, uc, attr); 336 return; 337 } 338 339 ri = (struct rasops_info *)cookie; 340 341 #ifdef RASOPS_CLIPPING 342 if ((unsigned)row >= (unsigned)ri->ri_rows) { 343 stamp_mutex--; 344 return; 345 } 346 347 if ((unsigned)col >= (unsigned)ri->ri_cols) { 348 stamp_mutex--; 349 return; 350 } 351 #endif 352 353 /* Recompute stamp? */ 354 if (attr != stamp_attr) 355 rasops24_makestamp(ri, attr); 356 357 rp = (int32_t *)(ri->ri_bits + row*ri->ri_yscale + col*ri->ri_xscale); 358 height = ri->ri_font->fontheight; 359 360 if (uc == (u_int)-1) { 361 int32_t c = stamp[0]; 362 while (height--) { 363 rp[0] = rp[1] = rp[2] = rp[3] = 364 rp[4] = rp[5] = rp[6] = rp[7] = rp[8] = c; 365 DELTA(rp, ri->ri_stride, int32_t *); 366 } 367 } else { 368 uc -= ri->ri_font->firstchar; 369 fr = (u_char *)ri->ri_font->data + uc*ri->ri_fontscale; 370 fs = ri->ri_font->stride; 371 372 while (height--) { 373 so = STAMP_SHIFT(fr[0], 1) & STAMP_MASK; 374 rp[0] = STAMP_READ(so); 375 rp[1] = STAMP_READ(so + 4); 376 rp[2] = STAMP_READ(so + 8); 377 378 so = STAMP_SHIFT(fr[0], 0) & STAMP_MASK; 379 rp[3] = STAMP_READ(so); 380 rp[4] = STAMP_READ(so + 4); 381 rp[5] = STAMP_READ(so + 8); 382 383 so = STAMP_SHIFT(fr[1], 1) & STAMP_MASK; 384 rp[6] = STAMP_READ(so); 385 rp[7] = STAMP_READ(so + 4); 386 rp[8] = STAMP_READ(so + 8); 387 388 fr += fs; 389 DELTA(rp, ri->ri_stride, int32_t *); 390 } 391 } 392 393 /* Do underline */ 394 if ((attr & 1) != 0) { 395 int32_t c = STAMP_READ(52); 396 397 DELTA(rp, -(ri->ri_stride << 1), int32_t *); 398 rp[0] = rp[1] = rp[2] = rp[3] = 399 rp[4] = rp[5] = rp[6] = rp[7] = rp[8] = c; 400 } 401 402 stamp_mutex--; 403 } 404 405 /* 406 * Put a single character. This is for 16-pixel wide fonts. 407 */ 408 void 409 rasops24_putchar16(cookie, row, col, uc, attr) 410 void *cookie; 411 int row, col; 412 u_int uc; 413 long attr; 414 { 415 struct rasops_info *ri; 416 int height, so, fs; 417 int32_t *rp; 418 u_char *fr; 419 420 /* Can't risk remaking the stamp if it's already in use */ 421 if (stamp_mutex++) { 422 stamp_mutex--; 423 rasops24_putchar(cookie, row, col, uc, attr); 424 return; 425 } 426 427 ri = (struct rasops_info *)cookie; 428 429 #ifdef RASOPS_CLIPPING 430 if ((unsigned)row >= (unsigned)ri->ri_rows) { 431 stamp_mutex--; 432 return; 433 } 434 435 if ((unsigned)col >= (unsigned)ri->ri_cols) { 436 stamp_mutex--; 437 return; 438 } 439 #endif 440 441 /* Recompute stamp? */ 442 if (attr != stamp_attr) 443 rasops24_makestamp(ri, attr); 444 445 rp = (int32_t *)(ri->ri_bits + row*ri->ri_yscale + col*ri->ri_xscale); 446 height = ri->ri_font->fontheight; 447 448 if (uc == (u_int)-1) { 449 int32_t c = stamp[0]; 450 while (height--) { 451 rp[0] = rp[1] = rp[2] = rp[3] = 452 rp[4] = rp[5] = rp[6] = rp[7] = 453 rp[8] = rp[9] = rp[10] = rp[11] = c; 454 DELTA(rp, ri->ri_stride, int32_t *); 455 } 456 } else { 457 uc -= ri->ri_font->firstchar; 458 fr = (u_char *)ri->ri_font->data + uc*ri->ri_fontscale; 459 fs = ri->ri_font->stride; 460 461 while (height--) { 462 so = STAMP_SHIFT(fr[0], 1) & STAMP_MASK; 463 rp[0] = STAMP_READ(so); 464 rp[1] = STAMP_READ(so + 4); 465 rp[2] = STAMP_READ(so + 8); 466 467 so = STAMP_SHIFT(fr[0], 0) & STAMP_MASK; 468 rp[3] = STAMP_READ(so); 469 rp[4] = STAMP_READ(so + 4); 470 rp[5] = STAMP_READ(so + 8); 471 472 so = STAMP_SHIFT(fr[1], 1) & STAMP_MASK; 473 rp[6] = STAMP_READ(so); 474 rp[7] = STAMP_READ(so + 4); 475 rp[8] = STAMP_READ(so + 8); 476 477 so = STAMP_SHIFT(fr[1], 0) & STAMP_MASK; 478 rp[9] = STAMP_READ(so); 479 rp[10] = STAMP_READ(so + 4); 480 rp[11] = STAMP_READ(so + 8); 481 482 DELTA(rp, ri->ri_stride, int32_t *); 483 fr += fs; 484 } 485 } 486 487 /* Do underline */ 488 if ((attr & 1) != 0) { 489 int32_t c = STAMP_READ(52); 490 491 DELTA(rp, -(ri->ri_stride << 1), int32_t *); 492 rp[0] = rp[1] = rp[2] = rp[3] = 493 rp[4] = rp[5] = rp[6] = rp[7] = 494 rp[8] = rp[9] = rp[10] = rp[11] = c; 495 } 496 497 stamp_mutex--; 498 } 499 #endif /* !RASOPS_SMALL */ 500 501 /* 502 * Erase rows. This is nice and easy due to alignment. 503 */ 504 void 505 rasops24_eraserows(cookie, row, num, attr) 506 void *cookie; 507 int row, num; 508 long attr; 509 { 510 int n9, n3, n1, cnt, stride, delta; 511 u_int32_t *dp, clr, stamp[3]; 512 struct rasops_info *ri; 513 514 /* 515 * If the color is gray, we can cheat and use the generic routines 516 * (which are faster, hopefully) since the r,g,b values are the same. 517 */ 518 if ((attr & 4) != 0) { 519 rasops_eraserows(cookie, row, num, attr); 520 return; 521 } 522 523 ri = (struct rasops_info *)cookie; 524 525 #ifdef RASOPS_CLIPPING 526 if (row < 0) { 527 num += row; 528 row = 0; 529 } 530 531 if ((row + num) > ri->ri_rows) 532 num = ri->ri_rows - row; 533 534 if (num <= 0) 535 return; 536 #endif 537 538 clr = ri->ri_devcmap[(attr >> 16) & 0xf] & 0xffffff; 539 stamp[0] = (clr << 8) | (clr >> 16); 540 stamp[1] = (clr << 16) | (clr >> 8); 541 stamp[2] = (clr << 24) | clr; 542 543 #if BYTE_ORDER == LITTLE_ENDIAN 544 if ((ri->ri_flg & RI_BSWAP) == 0) { 545 #else 546 if ((ri->ri_flg & RI_BSWAP) != 0) { 547 #endif 548 stamp[0] = swap32(stamp[0]); 549 stamp[1] = swap32(stamp[1]); 550 stamp[2] = swap32(stamp[2]); 551 } 552 553 /* 554 * XXX the wsdisplay_emulops interface seems a little deficient in 555 * that there is no way to clear the *entire* screen. We provide a 556 * workaround here: if the entire console area is being cleared, and 557 * the RI_FULLCLEAR flag is set, clear the entire display. 558 */ 559 if (num == ri->ri_rows && (ri->ri_flg & RI_FULLCLEAR) != 0) { 560 stride = ri->ri_stride; 561 num = ri->ri_height; 562 dp = (int32_t *)ri->ri_origbits; 563 delta = 0; 564 } else { 565 stride = ri->ri_emustride; 566 num *= ri->ri_font->fontheight; 567 dp = (int32_t *)(ri->ri_bits + row * ri->ri_yscale); 568 delta = ri->ri_delta; 569 } 570 571 n9 = stride / 36; 572 cnt = (n9 << 5) + (n9 << 2); /* (32*n9) + (4*n9) */ 573 n3 = (stride - cnt) / 12; 574 cnt += (n3 << 3) + (n3 << 2); /* (8*n3) + (4*n3) */ 575 n1 = (stride - cnt) >> 2; 576 577 while (num--) { 578 for (cnt = n9; cnt; cnt--) { 579 dp[0] = stamp[0]; 580 dp[1] = stamp[1]; 581 dp[2] = stamp[2]; 582 dp[3] = stamp[0]; 583 dp[4] = stamp[1]; 584 dp[5] = stamp[2]; 585 dp[6] = stamp[0]; 586 dp[7] = stamp[1]; 587 dp[8] = stamp[2]; 588 dp += 9; 589 } 590 591 for (cnt = n3; cnt; cnt--) { 592 dp[0] = stamp[0]; 593 dp[1] = stamp[1]; 594 dp[2] = stamp[2]; 595 dp += 3; 596 } 597 598 for (cnt = 0; cnt < n1; cnt++) 599 *dp++ = stamp[cnt]; 600 601 DELTA(dp, delta, int32_t *); 602 } 603 } 604 605 /* 606 * Erase columns. 607 */ 608 void 609 rasops24_erasecols(cookie, row, col, num, attr) 610 void *cookie; 611 int row, col, num; 612 long attr; 613 { 614 int n12, n4, height, cnt, slop, clr, stamp[3]; 615 struct rasops_info *ri; 616 int32_t *dp, *rp; 617 u_char *dbp; 618 619 /* 620 * If the color is gray, we can cheat and use the generic routines 621 * (which are faster, hopefully) since the r,g,b values are the same. 622 */ 623 if ((attr & 4) != 0) { 624 rasops_erasecols(cookie, row, col, num, attr); 625 return; 626 } 627 628 ri = (struct rasops_info *)cookie; 629 630 #ifdef RASOPS_CLIPPING 631 /* Catches 'row < 0' case too */ 632 if ((unsigned)row >= (unsigned)ri->ri_rows) 633 return; 634 635 if (col < 0) { 636 num += col; 637 col = 0; 638 } 639 640 if ((col + num) > ri->ri_cols) 641 num = ri->ri_cols - col; 642 643 if (num <= 0) 644 return; 645 #endif 646 647 rp = (int32_t *)(ri->ri_bits + row*ri->ri_yscale + col*ri->ri_xscale); 648 num *= ri->ri_font->fontwidth; 649 height = ri->ri_font->fontheight; 650 651 clr = ri->ri_devcmap[(attr >> 16) & 0xf] & 0xffffff; 652 stamp[0] = (clr << 8) | (clr >> 16); 653 stamp[1] = (clr << 16) | (clr >> 8); 654 stamp[2] = (clr << 24) | clr; 655 656 #if BYTE_ORDER == LITTLE_ENDIAN 657 if ((ri->ri_flg & RI_BSWAP) == 0) { 658 #else 659 if ((ri->ri_flg & RI_BSWAP) != 0) { 660 #endif 661 stamp[0] = swap32(stamp[0]); 662 stamp[1] = swap32(stamp[1]); 663 stamp[2] = swap32(stamp[2]); 664 } 665 666 /* 667 * The current byte offset mod 4 tells us the number of 24-bit pels 668 * we need to write for alignment to 32-bits. Once we're aligned on 669 * a 32-bit boundary, we're also aligned on a 4 pixel boundary, so 670 * the stamp does not need to be rotated. The following shows the 671 * layout of 4 pels in a 3 word region and illustrates this: 672 * 673 * aaab bbcc cddd 674 */ 675 slop = (long)rp & 3; num -= slop; 676 n12 = num / 12; num -= (n12 << 3) + (n12 << 2); 677 n4 = num >> 2; num &= 3; 678 679 while (height--) { 680 dbp = (u_char *)rp; 681 DELTA(rp, ri->ri_stride, int32_t *); 682 683 /* Align to 4 bytes */ 684 /* XXX handle with masks, bring under control of RI_BSWAP */ 685 for (cnt = slop; cnt; cnt--) { 686 *dbp++ = (clr >> 16); 687 *dbp++ = (clr >> 8); 688 *dbp++ = clr; 689 } 690 691 dp = (int32_t *)dbp; 692 693 /* 12 pels per loop */ 694 for (cnt = n12; cnt; cnt--) { 695 dp[0] = stamp[0]; 696 dp[1] = stamp[1]; 697 dp[2] = stamp[2]; 698 dp[3] = stamp[0]; 699 dp[4] = stamp[1]; 700 dp[5] = stamp[2]; 701 dp[6] = stamp[0]; 702 dp[7] = stamp[1]; 703 dp[8] = stamp[2]; 704 dp += 9; 705 } 706 707 /* 4 pels per loop */ 708 for (cnt = n4; cnt; cnt--) { 709 dp[0] = stamp[0]; 710 dp[1] = stamp[1]; 711 dp[2] = stamp[2]; 712 dp += 3; 713 } 714 715 /* Trailing slop */ 716 /* XXX handle with masks, bring under control of RI_BSWAP */ 717 dbp = (u_char *)dp; 718 for (cnt = num; cnt; cnt--) { 719 *dbp++ = (clr >> 16); 720 *dbp++ = (clr >> 8); 721 *dbp++ = clr; 722 } 723 } 724 } 725