FDIF functioning as a user level driver.
[barrelfish] / usr / drivers / omap44xx / fdif / fdif.c
1 #include <stdio.h>
2 #include <stdlib.h>
3
4 #include <barrelfish/barrelfish.h>
5
6 #include <dev/omap/omap44xx_cam_prm_dev.h>
7 #include <dev/omap/omap44xx_cam_cm2_dev.h>
8 #include <dev/omap/omap44xx_fdif_dev.h>
9 #include <dev/omap/omap44xx_sr_mpu_dev.h>
10 #include <dev/omap/omap44xx_device_prm_dev.h>
11
12 #include "fdif.h"
13
14 #define PRINT_BUFFER_SIZE (1024*1024)
15 static char printbuf[PRINT_BUFFER_SIZE];
16
17 static omap44xx_cam_prm_t dev;
18 static omap44xx_fdif_t devfdif;
19 static omap44xx_cam_cm2_t devclk;
20 //static omap44xx_sr_mpu_t devvolt;
21 static omap44xx_device_prm_t devprm;
22
23 extern struct gimage lena_image;
24
25 // XXX: you need to have this functions in user space...
26 // not sure about these two, tough
27 //void cp15_invalidate_tlb(void);
28 //void cp15_invalidate_i_and_d_caches(void);
29
30 static lpaddr_t* vbase_glbl;
31
32 static void manage_clocks(void)
33 {
34     printf("Enable the clocks in domain CD_CAM\n");
35
36     // Clock domain CAM
37     lvaddr_t* vbase;
38     errval_t err;
39     err = map_device_register(0x4A009000, 4096, &vbase);
40     assert(err_is_ok(err));
41     FDIF_DEBUG("vbase points to %p\n", vbase);
42
43     omap44xx_cam_cm2_initialize(&devclk, (mackerel_addr_t)vbase);
44     //omap44xx_cam_cm2_pm_cam_pwrstctrl_powerstate_wrf(&dev, omap44xx_cam_prm_POWERSTATE_2);
45     omap44xx_cam_cm2_cm_cam_clkstctrl_clktrctrl_wrf(&devclk, 0x2);
46     omap44xx_cam_cm2_cm_cam_fdif_clkctrl_modulemode_wrf(&devclk, 0x2);
47
48     //omap44xx_cam_cm2_pr(printbuf, PRINT_BUFFER_SIZE, &devclk);
49     //printf("%s\n", printbuf);
50
51     //printf("Enable all the dependencies we can\n");
52     //omap44xx_cam_cm2_cm_cam_staticdep_l3_1_statdep_wrf(&devclk, 0x1);
53     //omap44xx_cam_cm2_cm_cam_staticdep_memif_statdep_wrf(&devclk, 0x1);
54     //omap44xx_cam_cm2_cm_cam_staticdep_ivahd_statdep_wrf(&devclk, 0x1);
55
56     //omap44xx_cam_cm2_pr(printbuf, PRINT_BUFFER_SIZE, &devclk);
57     //printf("%s\n", printbuf);
58
59
60     printf("Handle voltage for domain: VDD_CORE_L\n");
61     
62     // TODO access to smartreflex register not working, why?
63     //offset = (0x4A0DD000 & ARM_L1_SECTION_MASK);
64     //omap44xx_sr_mpu_initialize(&devvolt, (mackerel_addr_t)vbase+offset);
65     //omap44xx_sr_mpu_srstatus_pr(printbuf, PRINT_BUFFER_SIZE-1, &devvolt);
66     //printf("%s\n", printbuf);
67
68     err = map_device_register(0x4A307000, 4096, &vbase_glbl);
69     assert(err_is_ok(err));
70     lpaddr_t offset = (0x4A307B00 & 0xFFF);
71     omap44xx_device_prm_initialize(&devprm, (mackerel_addr_t)vbase_glbl+offset);
72     //omap44xx_device_prm_pr(printbuf, PRINT_BUFFER_SIZE, &devprm);
73     //printf("%s\n", printbuf);
74
75     // Init voltage controller
76     printf("Done handling voltage\n");
77 }
78
79 static void manage_power(void) 
80 {
81     printf("Power-on the PD_CAM domain for fdif\n");
82
83     // Power domain CAM
84     lvaddr_t* vbase;
85     errval_t err;
86     err = map_device_register(0x4A307000, 4096, &vbase);
87     assert(err_is_ok(err));
88
89     omap44xx_cam_prm_initialize(&dev, (mackerel_addr_t)vbase);
90     omap44xx_cam_prm_pm_cam_pwrstctrl_powerstate_wrf(&dev, omap44xx_cam_prm_POWERSTATE_3);
91
92     while(omap44xx_cam_prm_pm_cam_pwrstst_powerstatest_rdf(&dev)
93           != omap44xx_cam_prm_POWERSTATEST_3_r)
94     {}
95
96     //omap44xx_cam_prm_pr(printbuf, PRINT_BUFFER_SIZE, &dev);
97     //printf("%s\n", printbuf);
98
99     // Face detect Module
100     err = map_device_register(0x4A10A000, 4096, &vbase);
101     assert(err_is_ok(err));
102
103     omap44xx_fdif_initialize(&devfdif, (mackerel_addr_t)vbase);
104
105     // Set this to 0x1 to force the device off the standby mode
106     omap44xx_fdif_fdif_sysconfig_standbymode_wrf(&devfdif, 0x2);
107
108     omap44xx_fdif_fdif_sysconfig_pr(printbuf, PRINT_BUFFER_SIZE, &devfdif);
109     printf("%s\n", printbuf);
110
111     omap44xx_cam_cm2_pr(printbuf, PRINT_BUFFER_SIZE, &devclk);
112     printf("%s\n", printbuf);
113
114 }
115
116 int main(void) {
117     init_memory_manager();
118
119     manage_clocks();
120     manage_power();
121     //manage_voltage();
122
123     printf("FDIF Global Initialization\n");
124     omap44xx_fdif_fdif_sysconfig_softreset_wrf(&devfdif, 1);
125     while (omap44xx_fdif_fdif_sysconfig_softreset_rdf(&devfdif) != 0);
126
127     omap44xx_fdif_fdif_ctrl_max_tags_wrf(&devfdif, 0xA);
128
129     omap44xx_fdif_fdif_irqenable_set_finish_irq_wrf(&devfdif, 0, 1);
130     omap44xx_fdif_fdif_irqenable_set_finish_irq_wrf(&devfdif, 1, 1);
131     omap44xx_fdif_fdif_irqenable_set_finish_irq_wrf(&devfdif, 2, 1);
132
133     printf("Polling Method\n");
134     printf("Set Image Parameters\n");
135
136     size_t img_size = 320*240*8; // 75 KB
137     size_t working_size = img_size; // 51.25 KB is enough
138     size_t retbytes;
139     void* workarea;
140     uint8_t* image;
141     errval_t err;
142
143     struct capref img_cap;
144     struct capref workarea_cap;
145
146     err = frame_alloc(&img_cap, img_size, &retbytes);
147     assert(err_is_ok(err));
148     assert(retbytes >= img_size);
149
150     err = frame_alloc(&workarea_cap, working_size, &retbytes);
151     assert(err_is_ok(err));
152     assert(retbytes >= working_size);
153
154     err = vspace_map_one_frame((void**)&image, img_size, img_cap,
155                               NULL, NULL);
156     assert(err_is_ok(err));
157     err = vspace_map_one_frame(&workarea, working_size, workarea_cap,
158                               NULL, NULL);
159     assert(err_is_ok(err));
160
161     printf("Set up the image ...\n");
162     printf("RGB image type: width:%d height:%d bytes/pixel:%d\n", lena_image.width, lena_image.height, lena_image.bytes_per_pixel);
163     printf("Convert to grayscale, store in image buffer...\n");
164
165     for (int i=0; i<lena_image.width*lena_image.height; i+=1) {
166         image[i] = lena_image.pixel_data[i];
167     }
168
169     // TODO We should make sure here that image is actually fully in memory
170     // and not still hanging around in the cache
171
172     // Does this do cache to mem writeback?
173     //cp15_invalidate_tlb();
174     //cp15_invalidate_i_and_d_caches();
175     struct frame_identity ret;
176     err = invoke_frame_identify(img_cap, &ret);
177     assert (err_is_ok(err));
178     omap44xx_fdif_fdif_picaddr_wr(&devfdif, ret.base); // make sure 5 least significant bits are 0!
179
180     err = invoke_frame_identify(workarea_cap, &ret);
181     assert (err_is_ok(err));
182     omap44xx_fdif_fdif_wkaddr_wr(&devfdif, ret.base); // make sure 5 least significant bits are 0!
183     
184     omap44xx_fdif_fd_dcond_min_wrf(&devfdif, 0x0); // 40 pixel
185     omap44xx_fdif_fd_dcond_dir_wrf(&devfdif, 0x0); // up?
186
187     omap44xx_fdif_fd_startx_startx_wrf(&devfdif, 0x0);
188     omap44xx_fdif_fd_starty_starty_wrf(&devfdif, 0x0);
189
190     omap44xx_fdif_fd_sizex_sizex_wrf(&devfdif, 0x140); // TODO
191     omap44xx_fdif_fd_sizey_sizey_wrf(&devfdif, 0xf0); // TODO
192     omap44xx_fdif_fd_lhit_lhit_wrf(&devfdif, 0x5);
193
194     omap44xx_fdif_fd_ctrl_run_wrf(&devfdif, 0x1);
195
196     while(omap44xx_fdif_fd_ctrl_finish_rdf(&devfdif) != 0x1);
197
198     printf("Face detection completed:\n");
199     printf("Read the results...\n");
200     
201     int faces = omap44xx_fdif_fd_dnum_dnum_rdf(&devfdif);
202     printf("Faces found: %d\n", faces);
203     //omap44xx_fdif_pr(printbuf, PRINT_BUFFER_SIZE, &devfdif);
204     //printf("%s\n", printbuf);
205
206     for (int i=0; i<faces; i++) {
207         printf("Face %d:\n", i);
208         int x = omap44xx_fdif_fd_centerx_centerx_rdf(&devfdif, i);
209         int y = omap44xx_fdif_fd_centery_centery_rdf(&devfdif, i);
210         printf("Position (X,Y): %d %d\n", x, y);
211
212         int size = omap44xx_fdif_fd_confsize_size_rdf(&devfdif, i);
213         int confidence = omap44xx_fdif_fd_confsize_conf_rdf(&devfdif, i);
214         int angle = omap44xx_fdif_fd_angle_angle_rdf(&devfdif, i);
215         printf("Size: %d Confidence: %d Angle: %d\n", size, confidence, angle);
216     }
217
218     return 0;
219 }