Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /*
- Copyright (C) 2013 by Brendan G Bohannon
- Email: cr88192@gmail.com
- Copying: http://pastebin.com/iJxtZHm6
- */
- /*
- DXTn packed images.
- Each block tag will be encoded in the form (byte):
- 0 <block:QWORD> Literal Block.
- 1-127 Single byte block index.
- 128-191 X Two byte block index (16384 blocks).
- 192-223 XX Three byte block index (2097152 blocks).
- 224-238 I LZ/RLE Run (2-16 blocks, Index)
- 239 LI LZ/RLE Run (Length, Index)
- 240 XXX 24-Bit Index
- 241 XXXX 32-Bit Index
- 242-246 Literal Blocks (2-6 Blocks)
- 247 L Literal Blocks (L Blocks)
- 248-255 Reserved
- The block index will indicate how many blocks backwards to look for a matching block (1 will repeat the prior block).
- Length/Index values will use the same organization as above, only limited to encoding numeric values.
- 0-127 0-127.
- 128-191 X 128-16383.
- 192-223 XX 16384-2097151.
- 240 XXX 24-Bit Index (0-16777215)
- 241 XXXX 32-Bit Index (0-4294967295)
- Note that DXT5 images will be split into 2 block-planes, with the first encoding the alpha component, followed by the plane encoding the RGB components.
- */
- byte *BGBBTJ_PackBCn_DecodeValue(byte *cs, int *rval)
- {
- int op, i;
- op=*cs++;
- if(op<128)
- { *rval=op; return(cs); }
- if(op<192)
- {
- *rval=((op-128)<<8)|(*cs++);
- return(cs);
- }
- if(op<224)
- {
- i=((op-192)<<8)|(*cs++);
- i=(i<<8)|(*cs++);
- *rval=i;
- return(cs);
- }
- if(op==240)
- {
- i=*cs++;
- i=(i<<8)|(*cs++);
- i=(i<<8)|(*cs++);
- *rval=i;
- return(cs);
- }
- if(op==241)
- {
- i=*cs++; i=(i<<8)|(*cs++);
- i=(i<<8)|(*cs++); i=(i<<8)|(*cs++);
- *rval=i;
- return(cs);
- }
- return(cs);
- }
- byte *BGBBTJ_PackBCn_DecodeRun(byte *cs, int *ridx, int *rlen)
- {
- int op, i;
- op=*cs++;
- if(!op)
- { *ridx=0; *rlen=0; return(cs); }
- if(op<128)
- { *ridx=op; *rlen=1; return(cs); }
- if(op<192)
- {
- *ridx=((op-128)<<8)|(*cs++);
- *rlen=1;
- return(cs);
- }
- if(op<224)
- {
- i=((op-192)<<8)|(*cs++);
- i=(i<<8)|(*cs++);
- *ridx=i;
- *rlen=1;
- return(cs);
- }
- if(op<239)
- {
- cs=BGBBTJ_PackBCn_DecodeValue(cs, ridx);
- *rlen=(op-224)+2;
- return(cs);
- }
- if(op==239)
- {
- cs=BGBBTJ_PackBCn_DecodeValue(cs, rlen);
- cs=BGBBTJ_PackBCn_DecodeValue(cs, ridx);
- return(cs);
- }
- if(op==240)
- {
- i=*cs++;
- i=(i<<8)|(*cs++);
- i=(i<<8)|(*cs++);
- *ridx=i;
- *rlen=1;
- return(cs);
- }
- if(op==241)
- {
- i=*cs++; i=(i<<8)|(*cs++);
- i=(i<<8)|(*cs++); i=(i<<8)|(*cs++);
- *ridx=i;
- *rlen=1;
- return(cs);
- }
- if(op<247)
- {
- *ridx=0;
- *rlen=(op-242)+2;
- return(cs);
- }
- if(op==247)
- {
- *ridx=0;
- cs=BGBBTJ_PackBCn_DecodeValue(cs, rlen);
- return(cs);
- }
- *ridx=0; *rlen=0;
- return(cs);
- }
- byte *BGBBTJ_PackBCn_DecodeBlockArray(byte *ibuf, byte *blks,
- int count, int stride)
- {
- byte *cs, *ct, *cte, *cs1, *ct1, *cs1e;
- int bi, bl;
- int i, j;
- cs=ibuf; ct=blks; cte=ct+count*stride;
- while(ct<cte)
- {
- cs=BGBBTJ_PackBCn_DecodeRun(cs, &bi, &bl);
- if(bi==0)
- {
- if(bl>1)
- {
- #if defined(X86) || defined(X86_64)
- cs1e=cs+bl*8;
- while(cs<cs1e)
- {
- *(u64 *)ct=*(u64 *)(cs);
- cs+=8; ct+=stride;
- }
- #else
- for(i=0; i<bl; i++)
- { memcpy(ct+i*stride, cs+i*8, 8); }
- cs+=bl*8;
- ct+=bl*stride;
- #endif
- continue;
- }
- #if defined(X86) || defined(X86_64)
- *(u64 *)ct=*(u64 *)cs;
- #else
- memcpy(ct, cs, 8);
- #endif
- ct+=stride; cs+=8;
- continue;
- }
- #if defined(X86) || defined(X86_64)
- cs1=ct-bi*stride;
- cs1e=cs1+bl*stride;
- while(cs1<cs1e)
- {
- *(u64 *)ct=*(u64 *)(cs1);
- cs1+=stride; ct+=stride;
- }
- #else
- for(i=0; i<bl; i++)
- { memcpy(ct+i*stride, ct+(i-bi)*stride, 8); }
- ct+=bl*stride;
- #endif
- }
- return(cs);
- }
- BGBBTJ_API int BGBBTJ_PackBCn_DecodeBlocksDXT5(
- byte *ibuf, byte *blks, int count)
- {
- byte *cs;
- cs=BGBBTJ_PackBCn_DecodeBlockArray(ibuf, blks, count, 16);
- cs=BGBBTJ_PackBCn_DecodeBlockArray(cs, blks+8, count, 16);
- return(cs-ibuf);
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement