Subversion Repositories planix.SVN

Rev

Rev 2 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 - 1
#include <u.h>
2
#include <libc.h>
3
#include <draw.h>
4
#include <memdraw.h>
5
 
6
int
7
cloadmemimage(Memimage *i, Rectangle r, uchar *data, int ndata)
8
{
9
	int y, bpl, c, cnt, offs;
10
	uchar mem[NMEM], *memp, *omemp, *emem, *linep, *elinep, *u, *eu;
11
 
12
	if(!rectinrect(r, i->r))
13
		return -1;
14
	bpl = bytesperline(r, i->depth);
15
	u = data;
16
	eu = data+ndata;
17
	memp = mem;
18
	emem = mem+NMEM;
19
	y = r.min.y;
20
	linep = byteaddr(i, Pt(r.min.x, y));
21
	elinep = linep+bpl;
22
	for(;;){
23
		if(linep == elinep){
24
			if(++y == r.max.y)
25
				break;
26
			linep = byteaddr(i, Pt(r.min.x, y));
27
			elinep = linep+bpl;
28
		}
29
		if(u == eu){	/* buffer too small */
30
			return -1;
31
		}
32
		c = *u++;
33
		if(c >= 128){
34
			for(cnt=c-128+1; cnt!=0 ;--cnt){
35
				if(u == eu){		/* buffer too small */
36
					return -1;
37
				}
38
				if(linep == elinep){	/* phase error */
39
					return -1;
40
				}
41
				*linep++ = *u;
42
				*memp++ = *u++;
43
				if(memp == emem)
44
					memp = mem;
45
			}
46
		}
47
		else{
48
			if(u == eu)	/* short buffer */
49
				return -1;
50
			offs = *u++ + ((c&3)<<8)+1;
51
			if(memp-mem < offs)
52
				omemp = memp+(NMEM-offs);
53
			else
54
				omemp = memp-offs;
55
			for(cnt=(c>>2)+NMATCH; cnt!=0; --cnt){
56
				if(linep == elinep)	/* phase error */
57
					return -1;
58
				*linep++ = *omemp;
59
				*memp++ = *omemp++;
60
				if(omemp == emem)
61
					omemp = mem;
62
				if(memp == emem)
63
					memp = mem;
64
			}
65
		}
66
	}
67
	return u-data;
68
}