* progress in moving all the fileaccess over to a wrapper system that can do fd based...
[rrdtool.git] / src / rrd_first.c
1 /*****************************************************************************
2  * RRDtool 1.2.23  Copyright by Tobi Oetiker, 1997-2007
3  *****************************************************************************
4  * rrd_first Return
5  *****************************************************************************
6  * Initial version by Burton Strauss, ntopSupport.com - 3/2005
7  *****************************************************************************/
8
9 #include "rrd_tool.h"
10
11
12 time_t
13 rrd_first(int argc, char **argv)
14 {
15     int target_rraindex=0;
16     char *endptr;
17     optind = 0; opterr = 0;  /* initialize getopt */
18
19     while (1){
20         static struct option long_options[] =
21         {
22             {"rraindex", required_argument, 0, 129},
23             {0,0,0,0}
24         };
25         int option_index = 0;
26         int opt;
27         opt = getopt_long(argc, argv, "", long_options, &option_index);
28
29         if(opt == EOF)
30             break;
31
32         switch(opt) {
33           case 129:
34             target_rraindex=strtol(optarg,&endptr,0);
35             if(target_rraindex < 0) {
36                 rrd_set_error("invalid rraindex number");
37                 return(-1);
38             }
39             break;
40           default:
41             rrd_set_error("usage rrdtool %s [--rraindex number] file.rrd", argv[0]);
42             return(-1);
43         }
44     }
45
46     if(optind >= argc){
47         rrd_set_error("not enough arguments");
48         return -1;       
49     }     
50
51     return(rrd_first_r(argv[optind], target_rraindex));
52 }
53
54
55 time_t
56 rrd_first_r(const char *filename, const int rraindex)
57 {
58     off_t rra_start,
59          timer;
60     time_t then;
61     rrd_t rrd;
62     rrd_file_t *rrd_file;
63
64     rrd_file = rrd_open(filename,&rrd, RRD_READONLY);
65     if (rrd_file == NULL) {
66         rrd_set_error("could not open RRD");
67         return(-1);
68     }
69
70     if((rraindex < 0) || (rraindex >= (int)rrd.stat_head->rra_cnt)) {
71         rrd_set_error("invalid rraindex number");
72         rrd_free(&rrd);
73         close(rrd_file->fd);
74         return(-1);
75     }
76
77     rra_start = rrd_file->header_len;
78     rrd_seek(rrd_file,
79           (rra_start +
80            (rrd.rra_ptr[rraindex].cur_row+1) *
81            rrd.stat_head->ds_cnt *
82            sizeof(rrd_value_t)),
83           SEEK_SET);
84     timer = - (rrd.rra_def[rraindex].row_cnt-1);
85     if (rrd.rra_ptr[rraindex].cur_row + 1 > rrd.rra_def[rraindex].row_cnt) {
86       rrd_seek(rrd_file,rra_start,SEEK_SET);
87     }
88     then = (rrd.live_head->last_up -
89             rrd.live_head->last_up %
90             (rrd.rra_def[rraindex].pdp_cnt*rrd.stat_head->pdp_step)) +
91            (timer * 
92             rrd.rra_def[rraindex].pdp_cnt*rrd.stat_head->pdp_step);
93
94     rrd_free(&rrd);
95     close(rrd_file->fd);
96     rrd_close(rrd_file);
97     return(then);
98 }
99