File: get.c

package info (click to toggle)
grass 6.4.4-1
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 104,028 kB
  • ctags: 40,409
  • sloc: ansic: 419,980; python: 63,559; tcl: 46,692; cpp: 29,791; sh: 18,564; makefile: 7,000; xml: 3,505; yacc: 561; perl: 559; lex: 480; sed: 70; objc: 7
file content (102 lines) | stat: -rw-r--r-- 2,244 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
#include <stdio.h>
#include <grass/rowio.h>

static void *my_select(ROWIO *, int);
static void pageout(ROWIO *, int);


/*!
 * \brief read a row
 *
 * Rowio_get() returns a
 * buffer which holds the data for row <b>n</b> from the file associated with
 * ROWIO structure <b>r.</b> If the row requested is not in memory, the
 * <b>getrow()</b> routine specified in <i>rowio_setup</i> is called to
 * read row <b>n</b> into memory and a pointer to the memory buffer containing
 * the row is returned. If the data currently in the buffer had been changed by
 * <i>rowio_put</i>, the <b>putrow()</b> routine specified in
 * <i>rowio_setup</i> is called first to write the changed row to disk. If row
 * <b>n</b> is already in memory, no disk read is done. The pointer to the data
 * is simply returned.
 * Return codes:
 * NULL <b>n</b> is negative, or
 * <b>getrow()</b> returned 0 (indicating an error condition).
 * !NULL pointer to buffer containing row <b>n.</b>
 *
 *  \param r
 *  \param n
 *  \return char * 
 */

void *rowio_get(ROWIO * R, int row)
{
    int i;
    int age;
    int cur;

    if (row < 0)
	return NULL;

    if (row == R->cur)
	return R->buf;

    for (i = 0; i < R->nrows; i++)
	if (row == R->rcb[i].row)
	    return my_select(R, i);

    age = 0;
    cur = 0;

    for (i = 0; i < R->nrows; i++)
	if (R->rcb[i].row < 0) {	/* free slot ! */
	    cur = i;
	    break;
	}
	else if (age < R->rcb[i].age) {
	    cur = i;
	    age = R->rcb[i].age;
	}

    pageout(R, cur);

    i = (*R->getrow) (R->fd, R->rcb[cur].buf, R->rcb[cur].row = row, R->len);
    R->rcb[cur].dirty = 0;
    if (!i) {
	R->rcb[cur].row = -1;
	if (cur == R->cur)
	    R->cur = -1;
	return NULL;
    }

    return my_select(R, cur);
}

void rowio_flush(ROWIO * R)
{
    int i;

    for (i = 0; i < R->nrows; i++)
	pageout(R, i);
}

static void pageout(ROWIO * R, int cur)
{
    if (R->rcb[cur].row < 0)
	return;
    if (!R->rcb[cur].dirty)
	return;
    (*R->putrow) (R->fd, R->rcb[cur].buf, R->rcb[cur].row, R->len);
    R->rcb[cur].dirty = 0;
}

static void *my_select(ROWIO * R, int n)
{
    int i;

    R->rcb[n].age = 0;
    for (i = 0; i < R->nrows; i++)
	R->rcb[i].age++;
    R->cur = R->rcb[n].row;
    R->buf = R->rcb[n].buf;
    return R->buf;
}