1 /* drivers/input/sensors/access/sc7660.c
2 *
3 * Copyright (C) 2012-2015 ROCKCHIP.
4 * Author: luowei <lw@rock-chips.com>
5 *
6 * This software is licensed under the terms of the GNU General Public
7 * License version 2, as published by the Free Software Foundation, and
8 * may be copied, distributed, and modified under those terms.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 */
16 #include <linux/interrupt.h>
17 #include <linux/i2c.h>
18 #include <linux/slab.h>
19 #include <linux/irq.h>
20 #include <linux/miscdevice.h>
21 #include <linux/gpio.h>
22 #include <linux/uaccess.h>
23 #include <asm/atomic.h>
24 #include <linux/delay.h>
25 #include <linux/input.h>
26 #include <linux/workqueue.h>
27 #include <linux/freezer.h>
28 #ifdef CONFIG_HAS_EARLYSUSPEND
29 #include <linux/earlysuspend.h>
30 #endif
31 #include <linux/sensor-dev.h>
32
33 #define SC7660_ENABLE 1
34 #define SC7660_XOUT_L 0x28
35 #define SC7660_XOUT_H 0x29
36 #define SC7660_YOUT_L 0x2A
37 #define SC7660_YOUT_H 0x2B
38 #define SC7660_ZOUT_L 0x2C
39 #define SC7660_ZOUT_H 0x2D
40 #define SC7660_MODE 0x20
41 #define SC7660_MODE1 0x21
42 #define SC7660_MODE2 0x22
43 #define SC7660_MODE3 0x23
44 #define SC7660_BOOT 0x24
45 #define SC7660_STATUS 0x27
46 #define SC7660_50HZ 0x40
47 #define SC7660_100HZ 0x50
48 #define SC7660_200HZ 0x60
49 #define SC7660_400HZ 0x70
50 #define SC7660_RANGE 32768
51
52
53
54 #define CALIBRATION_NUM 20//40
55 #define AXIS_X_Y_RANGE_LIMIT 200
56 #define AXIS_X_Y_AVG_LIMIT 400
57 #define AXIS_Z_RANGE 200
58 #define AXIS_Z_DFT_G 1000
59 #define GOTO_CALI 100
60 #define FAILTO_CALI 101
61 /* LIS3DH */
62 #define SC7660_PRECISION 12
63 #define SC7660_BOUNDARY (0x1 << (SC7660_PRECISION - 1))
64 #define SC7660_GRAVITY_STEP (SC7660_RANGE / SC7660_BOUNDARY)
65
66 #define SC7660_COUNT_AVERAGE 2
67
68 //#define CFG_GSENSOR_CALIBFILE "/data/data/com.actions.sensor.calib/files/gsensor_calib.txt"
69 /*noCreateAttr:the initial is 1-->no create attr. if created, change noCreateAttr to 0.*/
70 static int noCreateAttr = 1;
71
72
73
74
75 //static int sc7660_acc_get_data( int *xyz);
76
77 struct SC7660_acc{
78 int x;
79 int y;
80 int z;
81 } ;
82
83 static struct SC7660_acc offset;
84 //static int calibrated;
85 struct i2c_client *sc7660_client;
86
87 struct sensor_axis_average {
88 long x_average;
89 long y_average;
90 long z_average;
91 int count;
92 };
93
94 struct Cali_Data {
95 //mis p and n
96 unsigned char xpmis; //x axis positive mismatch to write
97 unsigned char xnmis; //x axis negtive mismatch to write
98 unsigned char ypmis;
99 unsigned char ynmis;
100 unsigned char zpmis;
101 unsigned char znmis;
102 //off p and n
103 unsigned char xpoff; //x axis positive offset to write
104 unsigned char xnoff; //x axis negtive offset to write
105 unsigned char ypoff;
106 unsigned char ynoff;
107 unsigned char zpoff;
108 unsigned char znoff;
109 //mid mis and off
110 unsigned char xmmis; //x axis middle mismatch to write
111 unsigned char ymmis; //y axis middle mismatch to write
112 unsigned char zmmis; //z axis middle mismatch to write
113 unsigned char xmoff; //x axis middle offset to write
114 unsigned char ymoff; //y axis middle offset to write
115 unsigned char zmoff; //z axis middle offset to write
116 //output p and n
117 signed int xpoutput; //x axis output of positive mismatch
118 signed int xnoutput; //x axis output of negtive mismatch
119 signed int ypoutput;
120 signed int ynoutput;
121 signed int zpoutput;
122 signed int znoutput;
123 //output
124 signed int xfoutput; //x axis the best or the temporary output
125 signed int yfoutput; //y axis the best or the temporary output
126 signed int zfoutput; //z axis the best or the temporary output
127 //final and temp flag
128 unsigned char xfinalf; //x axis final flag:if 1,calibration finished
129 unsigned char yfinalf; //y axis final flag:if 1,calibration finished
130 unsigned char zfinalf; //z axis final flag:if 1,calibration finished
131 unsigned char xtempf; //x axis temp flag:if 1,the step calibration finished
132 unsigned char ytempf; //y axis temp flag:if 1,the step calibration finished
133 unsigned char ztempf; //z axis temp flag:if 1,the step calibration finished
134
135 unsigned char xaddmis; //x axis mismtach register address
136 unsigned char yaddmis; //y axis mismtach register address
137 unsigned char zaddmis; //z axis mismtach register address
138 unsigned char xaddoff; //x axis offset register address
139 unsigned char yaddoff; //y axis offset register address
140 unsigned char zaddoff; //z axis offset register address
141
142 unsigned char (*MisDataSpaceConvert)(unsigned char continuous); //mismatch space convert function pointer
143 unsigned char (*OffDataSpaceConvert)(unsigned char continuous); //offset space convert function pointer
144
145 };
146
147
148
149 static struct sensor_axis_average axis_average;
150
Read_Reg(unsigned char reg)151 static unsigned char Read_Reg(unsigned char reg)
152 {
153 char buffer[3]={0};
154 *buffer = reg;
155 sensor_rx_data(sc7660_client, buffer,1);
156 return buffer[0];
157 }
158
159
Read_Output(char reg)160 static signed char Read_Output(char reg)
161 {
162
163 char buffer[3] = {0};
164 signed char acc_buf[6];
165 int index = 0;
166 int ret = 0;
167
168
169 while(1)
170 {
171 msleep(15);
172 *buffer = SC7660_STATUS;
173 ret = sensor_rx_data(sc7660_client, buffer,1);
174
175 if( (buffer[0] & 0x08) != 0 )
176 {
177 break;
178 }
179 //msleep(1);
180
181 index++;
182
183 if(index > 40)
184 break;
185 }
186
187 *buffer = SC7660_XOUT_L;
188 ret = sensor_rx_data(sc7660_client, buffer,1);
189 *buffer = SC7660_XOUT_H;
190 ret = sensor_rx_data(sc7660_client, buffer,1);
191 acc_buf[1] = buffer[0];
192
193 *buffer = SC7660_YOUT_L;
194 ret = sensor_rx_data(sc7660_client, buffer,1);
195 *buffer = SC7660_YOUT_H;
196 ret = sensor_rx_data(sc7660_client, buffer,1);
197 acc_buf[3] = buffer[0];
198
199 *buffer = SC7660_ZOUT_L;
200 ret = sensor_rx_data(sc7660_client, buffer,1);
201 *buffer = SC7660_ZOUT_H;
202 ret = sensor_rx_data(sc7660_client, buffer,1);
203 acc_buf[5] = buffer[0];
204
205 if(reg == 0x29)
206 {
207 return acc_buf[1];
208 }
209 else if(reg == 0x2b)
210 {
211 return acc_buf[3];
212 }
213 else if(reg == 0x2d)
214 {
215 return acc_buf[5];
216 }
217 else
218 return 0;
219 }
220
Read_Output_3axis(unsigned char * acc_buf)221 static void Read_Output_3axis(unsigned char *acc_buf)
222 {
223 char buffer[3] = {0};
224 int index = 0;
225 int ret = 0;
226 while(1){
227 msleep(20);
228 *buffer = SC7660_STATUS;
229 //ret = sensor_rx_data(sc7660_client, buffer,1);
230 buffer[0] = Read_Reg(0x27);
231 if( (buffer[0] & 0x08) != 0 ){break;}
232 index++;
233 if(index > 40)break;
234 }
235 //6 register data be read out
236 *buffer = SC7660_XOUT_L;
237 ret = sensor_rx_data(sc7660_client, buffer,1);
238 acc_buf[0] = buffer[0];
239 *buffer = SC7660_XOUT_H;
240 ret = sensor_rx_data(sc7660_client, buffer,1);
241 acc_buf[1] = buffer[0];
242
243 *buffer = SC7660_YOUT_L;
244 ret = sensor_rx_data(sc7660_client, buffer,1);
245 acc_buf[2] = buffer[0];
246 *buffer = SC7660_YOUT_H;
247 ret = sensor_rx_data(sc7660_client, buffer,1);
248 acc_buf[3] = buffer[0];
249
250 *buffer = SC7660_ZOUT_L;
251 ret = sensor_rx_data(sc7660_client, buffer,1);
252 acc_buf[4] = buffer[0];
253 *buffer = SC7660_ZOUT_H;
254 ret = sensor_rx_data(sc7660_client, buffer,1);
255 acc_buf[5] = buffer[0];
256 }
257
Write_Input(char addr,char thedata)258 static void Write_Input(char addr, char thedata)
259 {
260 int result;
261 result = sensor_write_reg(sc7660_client, addr, thedata);
262 }
263
264
265
tilt_3axis_mtp(signed int x,signed int y,signed int z)266 static void tilt_3axis_mtp(signed int x,signed int y,signed int z){
267 char buffer[6] = {0};
268 unsigned char buffer0[6] = {0};
269 unsigned char buffer1[6] = {0};
270 signed char mtpread[3]={0};
271 signed int xoutp,youtp,zoutp;
272 signed int xoutpt,youtpt,zoutpt;
273 signed char xtilt,ytilt,ztilt;
274 xoutp=youtp=zoutp=0;
275 xoutpt=youtpt=zoutpt=0;
276 xtilt=ytilt=ztilt=0;
277 Read_Output_3axis(buffer0);
278 Read_Output_3axis(buffer1);
279 //calculate the tilt with 12 ADC data
280 xoutpt = ((signed int)((buffer1[1]<<8)|buffer1[0]))>>4;
281 youtpt = ((signed int)((buffer1[3]<<8)|buffer1[2]))>>4;
282 zoutpt = ((signed int)((buffer1[5]<<8)|buffer1[4]))>>4;
283 //with relative value
284 xoutp = xoutpt-x*16;
285 youtp = youtpt-y*16;
286 zoutp = zoutpt-z*16;
287
288
289 //read out the tilt value in mtp to calculate the new
290 *buffer = 0x10;
291 sensor_rx_data(sc7660_client, buffer,1);
292 mtpread[0]=(signed char)buffer[0];
293
294 *buffer = 0x11;
295 sensor_rx_data(sc7660_client, buffer,1);
296 mtpread[1]=(signed char)buffer[0];
297
298 *buffer = 0x12;
299 sensor_rx_data(sc7660_client, buffer,1);
300 mtpread[2]=(signed char)buffer[0];
301
302
303 // mtpread[0]= (signed char)Read_One_Byte(0x3a, 0x10);
304 // mtpread[1]= (signed char)Read_One_Byte(0x3a, 0x11);
305 // mtpread[2]= (signed char)Read_One_Byte(0x3a, 0x12);
306
307 //calculate the new tilt mtp value
308 xtilt=(signed char)(xoutp/8)+ mtpread[0];
309 ytilt=(signed char)(youtp/8)+ mtpread[1];
310 ztilt=(signed char)(zoutp/8)+ mtpread[2];
311
312 //write the new into mtp
313 Write_Input(0x10,xtilt);
314 Write_Input(0x11,ytilt);
315 Write_Input(0x12,ztilt);
316
317 }
318
319 //正向
320 //255-0 map to 7f-0-80-ff
321 //
322 //255 map to 127(0x7f)
323 //254 map to 126(0x7e)
324 //. map to .
325 //129 map to 001(0x01)
326 //128 map to 000(0x00)
327 //127 map to 128(0x80)
328 //126 map to 129(0x81)
329 //. map to .
330 //001 map to 254(0xfe)
331 //000 map to 255(0xff)
forword_MisDataSpaceConvert(unsigned char continuous)332 static unsigned char forword_MisDataSpaceConvert(unsigned char continuous)
333 {
334 if(continuous >= 128)
335 return continuous - 128;
336 else
337 return 255 - continuous;
338 }
339
340 //反向
341 //255-0 map to ff-80-00-7f
342 //
343 //255 map to 255(0xff)
344 //254 map to 254(0xfe)
345 //. map to .
346 //129 map to 129(0x81)
347 //128 map to 128(0x80)
348
349 //127 map to 0(0x00)
350 //126 map to 1(0x01)
351 //. map to .
352 //001 map to 126(0x7e)
353 //000 map to 127(0x7f)
reverse_MisDataSpaceConvert(unsigned char continuous)354 static unsigned char reverse_MisDataSpaceConvert(unsigned char continuous)
355 {
356 if(continuous >= 128)
357 return continuous;
358 else
359 return 127 - continuous;
360 }
361
362 //reverse
363 //7f-0 map to 0-7f
364 //
365
reverse_OffDataSpaceConvert(unsigned char continuous)366 static unsigned char reverse_OffDataSpaceConvert(unsigned char continuous)
367 {
368 return 127 - continuous;
369 }
370
371 //forword
372 //7f-0 map to 0-7f
373 //
374
forword_OffDataSpaceConvert(unsigned char continuous)375 static unsigned char forword_OffDataSpaceConvert(unsigned char continuous)
376 {
377 return continuous;
378 }
379
check_output_set_finalflag(struct Cali_Data * pcalidata,unsigned char err)380 static void check_output_set_finalflag(struct Cali_Data *pcalidata,unsigned char err){
381
382 if(abs(pcalidata->xfoutput) < err){
383 //printk("line:%d Xcali finish!Final=%d\n",__LINE__,pcalidata->xfoutput);
384 pcalidata->xfinalf=1;
385 }
386 if(abs(pcalidata->yfoutput) < err){
387 //printk("line:%d Xcali finish!Final=%d\n",__LINE__,pcalidata->yfoutput);
388 pcalidata->yfinalf=1;
389 }
390 if(abs(pcalidata->zfoutput) < err){
391 //printk("line:%d Xcali finish!Final=%d\n",__LINE__,pcalidata->zfoutput);
392 pcalidata->zfinalf=1;
393 }
394
395 }
396
397 //set the tempflag xtempf-ytempf-ztempf upto the finalflag
check_finalflag_set_tempflag(struct Cali_Data * pcalidata)398 static void check_finalflag_set_tempflag(struct Cali_Data *pcalidata){
399 if(pcalidata->xfinalf){pcalidata->xtempf=1;}
400 if(pcalidata->yfinalf){pcalidata->ytempf=1;}
401 if(pcalidata->zfinalf){pcalidata->ztempf=1;}
402 }
403
404 //return ornot,upto xfinalf-yfinalf-zfinalf
check_flag_is_return(struct Cali_Data * pcalidata)405 static unsigned char check_flag_is_return(struct Cali_Data *pcalidata){
406 if((pcalidata->xfinalf) && (pcalidata->yfinalf) && (pcalidata->zfinalf))
407 {
408 //printk("line:%d Allcali finish!\n",__LINE__);
409 return 1;//xyz cali ok
410 }
411 else return 0;
412 }
413
414 //updata middle mismatch register with the new mismatch
updata_midmis_address(struct Cali_Data * pcalidata)415 static void updata_midmis_address(struct Cali_Data *pcalidata){
416 if(pcalidata->xtempf==0){
417 pcalidata->xmmis=(unsigned char)(((unsigned int)(pcalidata->xpmis) + (unsigned int)(pcalidata->xnmis))/2);
418 pcalidata->MisDataSpaceConvert = reverse_MisDataSpaceConvert;
419 Write_Input(pcalidata->xaddmis, (*(pcalidata->MisDataSpaceConvert))(pcalidata->xmmis));
420 }
421 if(pcalidata->ytempf==0){
422 pcalidata->ymmis=(unsigned char)(((unsigned int)(pcalidata->ypmis) + (unsigned int)(pcalidata->ynmis))/2);
423 pcalidata->MisDataSpaceConvert = forword_MisDataSpaceConvert;
424 Write_Input(pcalidata->yaddmis, (*(pcalidata->MisDataSpaceConvert))(pcalidata->ymmis));
425 }
426 if(pcalidata->ztempf==0){
427 pcalidata->zmmis=(unsigned char)(((unsigned int)(pcalidata->zpmis) + (unsigned int)(pcalidata->znmis))/2);
428 pcalidata->MisDataSpaceConvert = reverse_MisDataSpaceConvert;
429 Write_Input(pcalidata->zaddmis, (*(pcalidata->MisDataSpaceConvert))(pcalidata->zmmis));
430 }
431 }
432
433 //updata middle offset register with the new offset
updata_midoff_address(struct Cali_Data * pcalidata)434 static void updata_midoff_address(struct Cali_Data *pcalidata){
435 if(pcalidata->xtempf==0){
436 pcalidata->xmoff=(unsigned char)(((unsigned int)(pcalidata->xpoff) + (unsigned int)(pcalidata->xnoff))/2);
437 pcalidata->OffDataSpaceConvert = reverse_OffDataSpaceConvert;
438 Write_Input(pcalidata->xaddoff, (*(pcalidata->OffDataSpaceConvert))(pcalidata->xmoff));
439 }
440 if(pcalidata->ytempf==0){
441 pcalidata->ymoff=(unsigned char)(((unsigned int)(pcalidata->ypoff) + (unsigned int)(pcalidata->ynoff))/2);
442 pcalidata->OffDataSpaceConvert = forword_OffDataSpaceConvert;
443 Write_Input(pcalidata->yaddoff, (*(pcalidata->OffDataSpaceConvert))(pcalidata->ymoff));
444 }
445 if(pcalidata->ztempf==0){
446 pcalidata->zmoff=(unsigned char)(((unsigned int)(pcalidata->zpoff) + (unsigned int)(pcalidata->znoff))/2);
447 pcalidata->OffDataSpaceConvert = forword_OffDataSpaceConvert;
448 Write_Input(pcalidata->zaddoff, (*(pcalidata->OffDataSpaceConvert))(pcalidata->zmoff));
449 }
450 }
451
452
453
454
updata_mmis_pnfoutput_set_tempflag(struct Cali_Data * pcalidata,unsigned char * buf,signed int xrel,signed int yrel,signed int zrel)455 static void updata_mmis_pnfoutput_set_tempflag( struct Cali_Data *pcalidata,
456 unsigned char *buf,
457 signed int xrel,
458 signed int yrel,
459 signed int zrel){
460 //output 2 struct data
461 pcalidata->xfoutput=(signed int)((signed char)buf[1])-xrel;
462 pcalidata->yfoutput=(signed int)((signed char)buf[3])-yrel;
463 pcalidata->zfoutput=(signed int)((signed char)buf[5])-zrel;
464
465 if(abs(pcalidata->xfoutput)<25)pcalidata->xtempf=1;
466 if(abs(pcalidata->yfoutput)<25)pcalidata->ytempf=1;
467 if(abs(pcalidata->zfoutput)<25)pcalidata->ztempf=1;
468
469 if(pcalidata->xtempf==0)
470 {
471 if(pcalidata->xfoutput>0){
472 pcalidata->xpoutput = pcalidata->xfoutput;
473 pcalidata->xpmis = pcalidata->xmmis;
474 }
475 else{
476 pcalidata->xnoutput = pcalidata->xfoutput;
477 pcalidata->xnmis = pcalidata->xmmis;
478 }
479 }
480
481 if(pcalidata->ytempf==0)
482 {
483 if(pcalidata->yfoutput>0){
484 pcalidata->ypoutput = pcalidata->yfoutput;
485 pcalidata->ypmis = pcalidata->ymmis;
486 }
487 else{
488 pcalidata->ynoutput = pcalidata->yfoutput;
489 pcalidata->ynmis = pcalidata->ymmis;
490 }
491 }
492
493 if(pcalidata->ztempf==0)
494 {
495 if(pcalidata->zfoutput>0){
496 pcalidata->zpoutput = pcalidata->zfoutput;
497 pcalidata->zpmis = pcalidata->zmmis;
498 }
499 else{
500 pcalidata->znoutput = pcalidata->zfoutput;
501 pcalidata->znmis = pcalidata->zmmis;
502 }
503 }
504 }
505
updata_moff_pnfoutput_set_tempflag(struct Cali_Data * pcalidata,unsigned char * buf,signed int xrel,signed int yrel,signed int zrel)506 static void updata_moff_pnfoutput_set_tempflag( struct Cali_Data *pcalidata,
507 unsigned char *buf,
508 signed int xrel,
509 signed int yrel,
510 signed int zrel){
511 //output 2 struct data
512 pcalidata->xfoutput=(signed int)((signed char)buf[1])-xrel;
513 pcalidata->yfoutput=(signed int)((signed char)buf[3])-yrel;
514 pcalidata->zfoutput=(signed int)((signed char)buf[5])-zrel;
515
516 if(abs(pcalidata->xfoutput)<3)pcalidata->xtempf=1;
517 if(abs(pcalidata->yfoutput)<3)pcalidata->ytempf=1;
518 if(abs(pcalidata->zfoutput)<3)pcalidata->ztempf=1;
519
520 if(pcalidata->xtempf==0)
521 {
522 if(pcalidata->xfoutput>0){
523 pcalidata->xpoutput = pcalidata->xfoutput;
524 pcalidata->xpoff = pcalidata->xmoff;
525 }
526 else{
527 pcalidata->xnoutput = pcalidata->xfoutput;
528 pcalidata->xnoff = pcalidata->xmoff;
529 }
530 }
531
532 if(pcalidata->ytempf==0)
533 {
534 if(pcalidata->yfoutput>0){
535 pcalidata->ypoutput = pcalidata->yfoutput;
536 pcalidata->ypoff = pcalidata->ymoff;
537 }
538 else{
539 pcalidata->ynoutput = pcalidata->yfoutput;
540 pcalidata->ynoff = pcalidata->ymoff;
541 }
542 }
543
544 if(pcalidata->ztempf==0)
545 {
546 if(pcalidata->zfoutput>0){
547 pcalidata->zpoutput = pcalidata->zfoutput;
548 pcalidata->zpoff = pcalidata->zmoff;
549 }
550 else{
551 pcalidata->znoutput = pcalidata->zfoutput;
552 pcalidata->znoff = pcalidata->zmoff;
553 }
554 }
555 }
556
auto_calibration_instant(signed int x,signed int y,signed int z)557 static int auto_calibration_instant(signed int x, signed int y, signed int z){
558
559 unsigned char count=0,cyclecount=0;
560 unsigned char acc_buf[6];
561 struct Cali_Data calidata={0};
562
563 //===========================================================================
564 //===========================================================================
565 //step0=initialization
566 calidata.xaddmis = 0x40;
567 calidata.yaddmis = 0x41;
568 calidata.zaddmis = 0x42;
569 calidata.xaddoff = 0x47;
570 calidata.yaddoff = 0x48;
571 calidata.zaddoff = 0x49;
572 #ifdef PRINT
573 printf("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
574 (UINT)calidata.xfinalf,(UINT)calidata.xtempf,
575 (UINT)calidata.yfinalf,(UINT)calidata.ytempf,
576 (UINT)calidata.zfinalf,(UINT)calidata.ztempf
577 );
578 #endif
579
580 //===========================================================================
581 //===========================================================================
582 //step1=if output is ok?
583 Read_Output_3axis(acc_buf);
584 calidata.xfoutput=(signed int)((signed char)acc_buf[1])-x;
585 calidata.yfoutput=(signed int)((signed char)acc_buf[3])-y;
586 calidata.zfoutput=(signed int)((signed char)acc_buf[5])-z;
587 check_output_set_finalflag(&calidata,2);
588 if(check_flag_is_return(&calidata)){
589 printk("step1:=file=%s,line=%d\n",__FILE__,__LINE__);
590 return 1;
591 }
592 #ifdef PRINT
593 printf("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
594 (UINT)calidata.xfinalf,(UINT)calidata.xtempf,
595 (UINT)calidata.yfinalf,(UINT)calidata.ytempf,
596 (UINT)calidata.zfinalf,(UINT)calidata.ztempf
597 );
598 #endif
599
600
601
602
603
604 //===========================================================================
605 //===========================================================================
606 //step2=can cali?
607 //max output reasonable?
608 // calidata.zfinalf=1;
609 if(calidata.xfinalf==0){
610 Write_Input(calidata.xaddoff, 0x3f);//cali mis under off=0x3f
611 Write_Input(0x10, 0); //tilt clear
612 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
613 Write_Input(calidata.xaddmis, (*(calidata.MisDataSpaceConvert))(255)); // x mis to max
614 }
615 if(calidata.yfinalf==0){
616 Write_Input(calidata.yaddoff, 0x3f);//cali mis under off=0x3f
617 Write_Input(0x11, 0); //tilt clear
618 calidata.MisDataSpaceConvert = forword_MisDataSpaceConvert;
619 Write_Input(calidata.yaddmis, (*(calidata.MisDataSpaceConvert))(255)); // y mis to max
620 }
621 if(calidata.zfinalf==0){
622 Write_Input(calidata.zaddoff, 0x3f);//cali mis under off=0x3f
623 Write_Input(0x12, 0); //tilt clear
624 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
625 Write_Input(calidata.zaddmis, (*(calidata.MisDataSpaceConvert))(255)); // z mis to max
626 }
627
628 Read_Output_3axis(acc_buf);
629 calidata.xpoutput=calidata.xfoutput=(signed int)((signed char)acc_buf[1])-x;
630 calidata.ypoutput=calidata.yfoutput=(signed int)((signed char)acc_buf[3])-y;
631 calidata.zpoutput=calidata.zfoutput=(signed int)((signed char)acc_buf[5])-z;
632 printk("step 2 xnoutput = %d ynoutput = %d znoutput = %d \n",calidata.xnoutput,calidata.ynoutput,calidata.znoutput);
633 if((calidata.xpoutput<-25)||(calidata.ypoutput<-25)||(calidata.zpoutput<-25)){
634 printk("step2:=file=%s,line=%d\n",__FILE__,__LINE__);
635 sensor_write_reg(sc7660_client,0x13,0x01);//allen
636 Write_Input(0x1e, 0x15); //保存校准寄存器的修改
637 mdelay(300);
638 Write_Input(0x1e, 0);
639 return 0;
640 }//if the max output is smaller than -25,then errs
641
642 //min output reasonable?
643 if(calidata.xfinalf==0){
644 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
645 Write_Input(calidata.xaddmis, (*(calidata.MisDataSpaceConvert))(0)); // x mis to min
646 }
647 if(calidata.yfinalf==0){
648 calidata.MisDataSpaceConvert = forword_MisDataSpaceConvert;
649 Write_Input(calidata.yaddmis, (*(calidata.MisDataSpaceConvert))(0)); // y mis to min
650 }
651 if(calidata.zfinalf==0){
652 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
653 Write_Input(calidata.zaddmis, (*(calidata.MisDataSpaceConvert))(0)); // z mis to min
654 }
655 Read_Output_3axis(acc_buf);
656 calidata.xnoutput=calidata.xfoutput=(signed int)((signed char)acc_buf[1])-x;
657 calidata.ynoutput=calidata.yfoutput=(signed int)((signed char)acc_buf[3])-y;
658 calidata.znoutput=calidata.zfoutput=(signed int)((signed char)acc_buf[5])-z;
659 printk("step 2 xnoutput = %d ynoutput = %d znoutput = %d \n",calidata.xnoutput,calidata.ynoutput,calidata.znoutput);
660 if((calidata.xnoutput>25)||(calidata.ynoutput>25)||(calidata.znoutput>25)){
661 printk("step2:=file=%s,line=%d\n",__FILE__,__LINE__);
662 sensor_write_reg(sc7660_client,0x13,0x01);//allen
663 Write_Input(0x1e, 0x15); //保存校准寄存器的修改
664 mdelay(300);
665 Write_Input(0x1e, 0);
666
667 return 0;
668 }
669
670 //get the the smaller output,maybe the calibration finished
671 if(abs(calidata.xpoutput)<=abs(calidata.xnoutput)){
672 calidata.xfoutput=calidata.xpoutput;
673 calidata.xmmis=255;
674 }
675 else{
676 calidata.xfoutput=calidata.xnoutput;
677 calidata.xmmis=0;
678 }
679 if(abs(calidata.ypoutput)<=abs(calidata.ynoutput)){
680 calidata.yfoutput=calidata.ypoutput;
681 calidata.ymmis=255;
682 }
683 else{
684 calidata.yfoutput=calidata.ynoutput;
685 calidata.ymmis=0;
686 }
687 if(abs(calidata.zpoutput)<=abs(calidata.znoutput)){
688 calidata.zfoutput=calidata.zpoutput;
689 calidata.zmmis=255;
690 }
691 else{
692 calidata.zfoutput=calidata.znoutput;
693 calidata.zmmis=0;
694 }
695 //write the mismatch of the smaller output into register
696 if(calidata.xfinalf==0){
697 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
698 Write_Input(calidata.xaddmis, (*(calidata.MisDataSpaceConvert))(calidata.xmmis));
699 }
700 if(calidata.yfinalf==0){
701 calidata.MisDataSpaceConvert = forword_MisDataSpaceConvert;
702 Write_Input(calidata.yaddmis, (*(calidata.MisDataSpaceConvert))(calidata.ymmis));
703 }
704 if(calidata.zfinalf==0){
705 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
706 Write_Input(calidata.zaddmis, (*(calidata.MisDataSpaceConvert))(calidata.zmmis));
707 }
708 check_output_set_finalflag(&calidata,2);
709 //if the smaller output <25,the step3 mis is finished
710 if(abs(calidata.xfoutput)<25) calidata.xtempf=1;
711 if(abs(calidata.yfoutput)<25) calidata.ytempf=1;
712 if(abs(calidata.zfoutput)<25) calidata.ztempf=1;
713 //can cali?
714 //===========================================================================
715 //===========================================================================
716 //===========================================================================
717 //step3=cali mis for zero in 25 LSB
718 calidata.xpmis=calidata.ypmis=calidata.zpmis=255;
719 calidata.xnmis=calidata.ynmis=calidata.znmis=0;
720 check_finalflag_set_tempflag(&calidata);
721 #ifdef PRINT
722 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
723 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
724 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
725 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
726 );
727 #endif
728 cyclecount=0;
729 while(1){
730 if(++cyclecount>20)break;//if some errs happened,the cyclecount exceeded
731
732 if((calidata.xtempf)&&(calidata.ytempf)&&(calidata.ztempf))break;
733 updata_midmis_address(&calidata);
734 Read_Output_3axis(acc_buf);
735 calidata.xfoutput=(signed int)((signed char)acc_buf[1])-x;
736 calidata.yfoutput=(signed int)((signed char)acc_buf[3])-y;
737 calidata.zfoutput=(signed int)((signed char)acc_buf[5])-z;
738 #ifdef PRINT
739 printk("xp%4d=%4d,xm%4d=%4d,xn%4d=%4d, yp%4d=%4d,ym%4d=%4d,yn%4d=%4d, zp%4d=%4d,zm%4d=%4d,zn%4d=%4d\n\r",
740 calidata.xpoutput,(unsigned int)calidata.xpmis,
741 calidata.xfoutput,(unsigned int)calidata.xmmis,
742 calidata.xnoutput,(unsigned int)calidata.xnmis,
743 calidata.ypoutput,(unsigned int)calidata.ypmis,
744 calidata.yfoutput,(unsigned int)calidata.ymmis,
745 calidata.ynoutput,(unsigned int)calidata.ynmis,
746 calidata.zpoutput,(unsigned int)calidata.zpmis,
747 calidata.zfoutput,(unsigned int)calidata.zmmis,
748 calidata.znoutput,(unsigned int)calidata.znmis
749 );
750 #endif
751 updata_mmis_pnfoutput_set_tempflag(&calidata,acc_buf,x,y,z);
752 check_output_set_finalflag(&calidata,2);
753 if(check_flag_is_return(&calidata))return 1;
754 }
755 #ifdef PRINT
756 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
757 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
758 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
759 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
760 );
761 #endif
762 //cali mis for zero in 25 LSB
763 //===========================================================================
764
765
766 //===========================================================================
767 //===========================================================================
768 //step4=cali mis for rel and the most fit
769 calidata.xtempf=calidata.ytempf=calidata.ztempf=1;
770 if((calidata.xmmis>0)&&(calidata.xmmis<255))calidata.xtempf=0;
771 if((calidata.ymmis>0)&&(calidata.ymmis<255))calidata.ytempf=0;
772 if((calidata.zmmis>0)&&(calidata.zmmis<255))calidata.ztempf=0;
773 calidata.xpmis=calidata.xnmis=calidata.xmmis;
774 calidata.ypmis=calidata.ynmis=calidata.ymmis;
775 calidata.zpmis=calidata.znmis=calidata.zmmis;
776 for(count = 0; count < 3; count++)
777 {
778 if(calidata.xtempf==0){
779 calidata.xpmis = calidata.xmmis + count - 1;
780 if((calidata.xpmis>calidata.xmmis)&&(calidata.xpmis==128))calidata.xpmis = calidata.xmmis + count-1 + 1;
781 if((calidata.xpmis<calidata.xmmis)&&(calidata.xpmis==127))calidata.xpmis = calidata.xmmis + count-1 - 1;
782 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
783 Write_Input(calidata.xaddmis, (*(calidata.MisDataSpaceConvert))(calidata.xpmis));
784 }
785 if(calidata.ytempf==0){
786 calidata.ypmis = calidata.ymmis + count - 1;
787 if((calidata.ypmis>calidata.ymmis)&&(calidata.ypmis==128))calidata.ypmis = calidata.ymmis + count-1 + 1;
788 if((calidata.ypmis<calidata.ymmis)&&(calidata.ypmis==127))calidata.ypmis = calidata.ymmis + count-1 - 1;
789 calidata.MisDataSpaceConvert = forword_MisDataSpaceConvert;
790 Write_Input(calidata.yaddmis, (*(calidata.MisDataSpaceConvert))(calidata.ypmis));
791 }
792 if(calidata.ztempf==0){
793 calidata.zpmis = calidata.zmmis + count - 1;
794 if((calidata.zpmis>calidata.zmmis)&&(calidata.zpmis==128))calidata.zpmis = calidata.zmmis + count-1 + 1;
795 if((calidata.zpmis<calidata.zmmis)&&(calidata.zpmis==127))calidata.zpmis = calidata.zmmis + count-1 - 1;
796 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
797 Write_Input(calidata.zaddmis, (*(calidata.MisDataSpaceConvert))(calidata.zpmis));
798 }
799 Read_Output_3axis(acc_buf);
800 if(abs((signed int)((signed char)acc_buf[1])-x)<abs(calidata.xfoutput)){
801 calidata.xnmis=calidata.xpmis;
802 calidata.xfoutput= (signed int)((signed char)acc_buf[1])-x;
803 }
804 if(abs((signed int)((signed char)acc_buf[3])-y)<abs(calidata.yfoutput)){
805 calidata.ynmis=calidata.ypmis;
806 calidata.yfoutput= (signed int)((signed char)acc_buf[3])-y;
807 }
808 if(abs((signed int)((signed char)acc_buf[5])-z)<abs(calidata.zfoutput)){
809 calidata.znmis=calidata.zpmis;
810 calidata.zfoutput= (signed int)((signed char)acc_buf[5])-z;
811 }
812 if(calidata.xtempf==0){
813 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
814 Write_Input(calidata.xaddmis, (*(calidata.MisDataSpaceConvert))(calidata.xnmis));
815 }
816 if(calidata.ytempf==0){
817 calidata.MisDataSpaceConvert = forword_MisDataSpaceConvert;
818 Write_Input(calidata.yaddmis, (*(calidata.MisDataSpaceConvert))(calidata.ynmis));
819 }
820 if(calidata.ztempf==0){
821 calidata.MisDataSpaceConvert = reverse_MisDataSpaceConvert;
822 Write_Input(calidata.zaddmis, (*(calidata.MisDataSpaceConvert))(calidata.znmis));
823 }
824 #ifdef PRINT
825 printk("L%4d:xf=%4d,xmis=%4d,yf=%4d,ymis=%4d,zf=%4d,zmis=%4d\n\r",__LINE__,
826 (signed int)((signed char)acc_buf[1])-x,(unsigned int)calidata.xpmis,
827 (signed int)((signed char)acc_buf[3])-y,(unsigned int)calidata.ypmis,
828 (signed int)((signed char)acc_buf[5])-z,(unsigned int)calidata.zpmis
829 );
830 #endif
831
832 }
833 //Write_Input(AddMis, (*MisDataSpaceConvert)(FinaloutputMisConfiguration));
834 //===========================================================================
835 //===========================================================================
836 //step5=cali off for zero in 2 LSB
837 calidata.xpoff=calidata.ypoff=calidata.zpoff=0x7f;
838 calidata.xnoff=calidata.ynoff=calidata.znoff=0;
839 calidata.xtempf=calidata.ytempf=calidata.ztempf=0;
840 #ifdef PRINT
841 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
842 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
843 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
844 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
845 );
846 #endif
847 check_finalflag_set_tempflag(&calidata);
848 #ifdef PRINT
849 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
850 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
851 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
852 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
853 );
854 #endif
855 //offset max
856 if(calidata.xtempf==0){
857 calidata.OffDataSpaceConvert = reverse_OffDataSpaceConvert;
858 Write_Input(calidata.xaddoff, (*(calidata.OffDataSpaceConvert))(calidata.xpoff)); // x off to max
859 }
860 if(calidata.ytempf==0){
861 calidata.OffDataSpaceConvert = forword_OffDataSpaceConvert;
862 Write_Input(calidata.yaddoff, (*(calidata.OffDataSpaceConvert))(calidata.xpoff)); // y off to max
863 }
864 if(calidata.ztempf==0){
865 calidata.OffDataSpaceConvert = forword_OffDataSpaceConvert;
866 Write_Input(calidata.zaddoff, (*(calidata.OffDataSpaceConvert))(calidata.xpoff)); // z off to max
867 }
868 Read_Output_3axis(acc_buf);
869 calidata.xpoutput=calidata.xfoutput=(signed int)((signed char)acc_buf[1])-x;
870 calidata.ypoutput=calidata.yfoutput=(signed int)((signed char)acc_buf[3])-y;
871 calidata.zpoutput=calidata.zfoutput=(signed int)((signed char)acc_buf[5])-z;
872 #ifdef PRINT
873 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
874 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
875 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
876 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
877 );
878 #endif
879 check_output_set_finalflag(&calidata,2);
880 #ifdef PRINT
881 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
882 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
883 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
884 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
885 );
886 #endif
887 //offset min
888 if(calidata.xtempf==0){
889 calidata.OffDataSpaceConvert = reverse_OffDataSpaceConvert;
890 Write_Input(calidata.xaddoff, (*(calidata.OffDataSpaceConvert))(calidata.xnoff)); // x off to min
891 }
892 if(calidata.ytempf==0){
893 calidata.OffDataSpaceConvert = forword_OffDataSpaceConvert;
894 Write_Input(calidata.yaddoff, (*(calidata.OffDataSpaceConvert))(calidata.ynoff)); // y off to min
895 }
896 if(calidata.ztempf==0){
897 calidata.OffDataSpaceConvert = forword_OffDataSpaceConvert;
898 Write_Input(calidata.zaddoff, (*(calidata.OffDataSpaceConvert))(calidata.znoff)); // z off to min
899 }
900 Read_Output_3axis(acc_buf);
901 calidata.xnoutput=calidata.xfoutput=(signed int)((signed char)acc_buf[1])-x;
902 calidata.ynoutput=calidata.yfoutput=(signed int)((signed char)acc_buf[3])-y;
903 calidata.znoutput=calidata.zfoutput=(signed int)((signed char)acc_buf[5])-z;
904 #ifdef PRINT
905 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
906 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
907 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
908 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
909 );
910 #endif
911 check_output_set_finalflag(&calidata,2);
912 #ifdef PRINT
913 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
914 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
915 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
916 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
917 );
918 #endif
919 if(abs(calidata.xpoutput)<=abs(calidata.xnoutput)){
920 calidata.xfoutput=calidata.xpoutput;
921 calidata.xmoff=calidata.xpoff;
922 }
923 else{
924 calidata.xfoutput=calidata.xnoutput;
925 calidata.xmoff=calidata.xnoff;
926 }
927 if(abs(calidata.ypoutput)<=abs(calidata.ynoutput)){
928 calidata.yfoutput=calidata.ypoutput;
929 calidata.ymoff=calidata.ypoff;
930 }
931 else{
932 calidata.yfoutput=calidata.ynoutput;
933 calidata.ymoff=calidata.ynoff;
934 }
935 if(abs(calidata.zpoutput)<=abs(calidata.znoutput)){
936 calidata.zfoutput=calidata.zpoutput;
937 calidata.zmoff=calidata.zpoff;
938 }
939 else{
940 calidata.zfoutput=calidata.znoutput;
941 calidata.zmoff=calidata.znoff;
942 }
943 if(calidata.xtempf==0){
944 calidata.OffDataSpaceConvert = reverse_OffDataSpaceConvert;
945 Write_Input(calidata.xaddoff, (*(calidata.OffDataSpaceConvert))(calidata.xmoff));
946 }
947 if(calidata.ytempf==0){
948 calidata.OffDataSpaceConvert = forword_OffDataSpaceConvert;
949 Write_Input(calidata.yaddoff, (*(calidata.OffDataSpaceConvert))(calidata.ymoff));
950 }
951 if(calidata.ztempf==0){
952 calidata.OffDataSpaceConvert = forword_OffDataSpaceConvert;
953 Write_Input(calidata.zaddoff, (*(calidata.OffDataSpaceConvert))(calidata.zmoff));
954 }
955 if((calidata.xpoutput>0 && calidata.xnoutput>0)||(calidata.xpoutput<0 && calidata.xnoutput<0)){
956 calidata.xfinalf=1;
957 }
958
959 if((calidata.ypoutput>0 && calidata.ynoutput>0)||(calidata.ypoutput<0 && calidata.ynoutput<0)){
960 calidata.yfinalf=1;
961 }
962
963 if((calidata.zpoutput>0 && calidata.znoutput>0)||(calidata.zpoutput<0 && calidata.znoutput<0)){
964 calidata.zfinalf=1;
965 }
966
967
968 check_finalflag_set_tempflag(&calidata);
969 #ifdef PRINT
970 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
971 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
972 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
973 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
974 );
975 #endif
976 cyclecount=0;
977 while(1){
978 if(++cyclecount>20)break;
979
980 if((calidata.xtempf)&&(calidata.ytempf)&&(calidata.ztempf))break;
981 updata_midoff_address(&calidata);
982 Read_Output_3axis(acc_buf);
983 calidata.xfoutput=(signed int)((signed char)acc_buf[1])-x;
984 calidata.yfoutput=(signed int)((signed char)acc_buf[3])-y;
985 calidata.zfoutput=(signed int)((signed char)acc_buf[5])-z;
986 #ifdef PRINT
987 printk("xp%4d=%4d,xm%4d=%4d,xn%4d=%4d, yp%4d=%4d,ym%4d=%4d,yn%4d=%4d, zp%4d=%4d,zm%4d=%4d,zn%4d=%4d\n\r",
988 calidata.xpoutput,(unsigned int)calidata.xpoff,
989 calidata.xfoutput,(unsigned int)calidata.xmoff,
990 calidata.xnoutput,(unsigned int)calidata.xnoff,
991 calidata.ypoutput,(unsigned int)calidata.ypoff,
992 calidata.yfoutput,(unsigned int)calidata.ymoff,
993 calidata.ynoutput,(unsigned int)calidata.ynoff,
994 calidata.zpoutput,(unsigned int)calidata.zpoff,
995 calidata.zfoutput,(unsigned int)calidata.zmoff,
996 calidata.znoutput,(unsigned int)calidata.znoff
997 );
998 #endif
999 updata_moff_pnfoutput_set_tempflag(&calidata,acc_buf,x,y,z);
1000 check_output_set_finalflag(&calidata,2);
1001 if(check_flag_is_return(&calidata))return 1;
1002 }
1003 #ifdef PRINT
1004 printk("L%4d:xff=%4d,xtf=%4d,yff=%4d,ytf=%4d,zff=%4d,ztf=%4d\n\r",__LINE__,
1005 (unsigned int)calidata.xfinalf,(unsigned int)calidata.xtempf,
1006 (unsigned int)calidata.yfinalf,(unsigned int)calidata.ytempf,
1007 (unsigned int)calidata.zfinalf,(unsigned int)calidata.ztempf
1008 );
1009 #endif
1010 //cali mis for zero in 25 LSB
1011 //===========================================================================
1012
1013 return 1;
1014 }
1015
auto_calibration_instant_mtp(signed int x,signed int y,signed int z)1016 static int auto_calibration_instant_mtp(signed int x, signed int y, signed int z){
1017 unsigned char readbuf[3]={0};
1018 unsigned char buffer[6] = {0};
1019 //unsigned char tbuffer[6] = {0};
1020 signed int xoutp,youtp,zoutp;
1021 unsigned char xfinalf,yfinalf,zfinalf;
1022 char reg_13 = 0;
1023
1024 xoutp=youtp=zoutp=0;
1025 xfinalf=yfinalf=zfinalf=0;
1026
1027 if(auto_calibration_instant(x,y,z)==0)
1028 {
1029 printk("auto_calibration_instant ==0 \n");
1030 sensor_write_reg(sc7660_client, 0x1e,0x05);
1031 mdelay(100);
1032 sensor_write_reg(sc7660_client, 0x13,0x01);
1033
1034 sensor_write_reg(sc7660_client, 0x1e,0x15);
1035 mdelay(300);
1036 return 0;
1037 }
1038
1039 //msleep(20);
1040 tilt_3axis_mtp(x,y,z);
1041 Read_Output_3axis(buffer);
1042 xoutp=(signed int)((signed char)buffer[1])-x;
1043 youtp=(signed int)((signed char)buffer[3])-y;
1044 zoutp=(signed int)((signed char)buffer[5])-z;
1045
1046 if(abs(xoutp) < 2){xfinalf=1;}
1047 if(abs(youtp) < 2){yfinalf=1;}
1048 if(abs(zoutp) < 2){zfinalf=1;}
1049
1050
1051 //*tbuffer = 0x10;
1052 //sensor_rx_data(sc7660_client, tbuffer,1);
1053 readbuf[0]= Read_Reg(0x10);
1054 //*tbuffer = 0x40;
1055 //sensor_rx_data(sc7660_client, tbuffer,1);
1056 readbuf[1]= Read_Reg(0x40);
1057 //*tbuffer = 0x47;
1058 //sensor_rx_data(sc7660_client, tbuffer,1);
1059 readbuf[2]= Read_Reg(0x47);
1060 printk("L%4d:xtilt=%4d,xmis=%4d,xoff=%4d\n\r",__LINE__,
1061 (unsigned int)readbuf[0],
1062 (unsigned int)readbuf[1],
1063 (unsigned int)readbuf[2]
1064 );
1065 //*tbuffer = 0x11;
1066 //sensor_rx_data(sc7660_client, tbuffer,1);
1067 readbuf[0]= Read_Reg(0x11);
1068 //*tbuffer = 0x41;
1069 //sensor_rx_data(sc7660_client, tbuffer,1);
1070 readbuf[1]= Read_Reg(0x41);
1071 //*tbuffer = 0x48;
1072 //sensor_rx_data(sc7660_client, tbuffer,1);
1073 readbuf[2]= Read_Reg(0x48);
1074 printk("L%4d:ytilt=%4d,ymis=%4d,yoff=%4d\n\r",__LINE__,
1075 (unsigned int)readbuf[0],
1076 (unsigned int)readbuf[1],
1077 (unsigned int)readbuf[2]
1078 );
1079
1080 //*tbuffer = 0x12;
1081 //sensor_rx_data(sc7660_client, tbuffer,1);
1082 readbuf[0]= Read_Reg(0x12);
1083 //*tbuffer = 0x42;
1084 //sensor_rx_data(sc7660_client, tbuffer,1);
1085 readbuf[1]= Read_Reg(0x42);
1086 //*tbuffer = 0x49;
1087 //sensor_rx_data(sc7660_client, tbuffer,1);
1088 readbuf[2]= Read_Reg(0x49);
1089 printk("L%4d:ztilt=%4d,zmis=%4d,zoff=%4d\n\r",__LINE__,
1090 (unsigned int)readbuf[0],
1091 (unsigned int)readbuf[1],
1092 (unsigned int)readbuf[2]
1093 );
1094
1095 if(xfinalf && yfinalf && zfinalf)
1096 {
1097 sensor_write_reg(sc7660_client,0x13,0x01);//allen MTP
1098 reg_13 = sensor_read_reg(sc7660_client,0x13);
1099 printk("line %d reg_13 = %x\n",__LINE__,reg_13);
1100 Write_Input(0x1e, 0x15); //保存校准寄存器的修改
1101 mdelay(300);
1102 reg_13 = sensor_read_reg(sc7660_client,0x13);
1103 printk("line %d reg_13 = %x\n",__LINE__,reg_13);
1104 Write_Input(0x1e, 0);
1105
1106 printk(KERN_INFO "run calibration finished\n");
1107
1108 return 1;//xyz cali ok
1109 }
1110 else
1111 {
1112 sensor_write_reg(sc7660_client,0x13,0x01);//allen MTP
1113 reg_13 = sensor_read_reg(sc7660_client,0x13);
1114 printk("line %d reg_13 = %x\n",__LINE__,reg_13);
1115 Write_Input(0x1e, 0x15); //保存校准寄存器的修改
1116 mdelay(300);
1117 reg_13 = sensor_read_reg(sc7660_client,0x13);
1118 printk("line %d reg_13 = %x\n",__LINE__,reg_13);
1119 Write_Input(0x1e, 0);
1120 return 0;
1121 }
1122 }
1123
1124
1125
1126
1127
SC7660_3_axis_Calibration(struct device * dev,struct device_attribute * attr,const char * buf,size_t count)1128 static ssize_t SC7660_3_axis_Calibration(struct device *dev,struct device_attribute *attr ,const char *buf, size_t count)
1129 {
1130 //unsigned temp[3];
1131 //struct SC7660_acc acc={0,0,-64};
1132 unsigned adj_ok = 0;
1133
1134 Write_Input(0x1e, 0x05); //为校准寄存器的修改开放权限
1135 Write_Input(0x20, 0x77);
1136 adj_ok = auto_calibration_instant_mtp(0,0,-64);
1137 if(adj_ok )
1138 {
1139 Write_Input(0x1e, 0x15); //保存校准寄存器的修改
1140 mdelay(5);
1141 printk(KERN_INFO "run calibration finished\n");
1142 }
1143 else
1144 printk(KERN_INFO "run calibration not finished\n");
1145 mdelay(5);
1146 return 1;
1147 }
1148
1149
SC7660_calibration_reset_store(struct device * dev,struct device_attribute * attr,const char * buf,size_t count)1150 static ssize_t SC7660_calibration_reset_store(struct device *dev,
1151 struct device_attribute *attr,
1152 const char *buf, size_t count)
1153 {
1154 Read_Output(0x29);
1155 //printk(KERN_INFO "reset calibration finished\n");
1156 return count;
1157 }
1158
SC7660_calibration_value_show(struct device * dev,struct device_attribute * attr,char * buf)1159 static ssize_t SC7660_calibration_value_show(struct device *dev,
1160 struct device_attribute *attr, char *buf)
1161 {
1162 return sprintf(buf, "%d %d %d\n", offset.x,offset.y,offset.z);
1163 }
1164
SC7660_calibration_value_store(struct device * dev,struct device_attribute * attr,const char * buf,size_t count)1165 static ssize_t SC7660_calibration_value_store(struct device *dev,
1166 struct device_attribute *attr,
1167 const char *buf, size_t count)
1168 {
1169 int data[3];
1170 sscanf(buf, "%d %d %d", &data[0], &data[1], &data[2]);
1171 offset.x = data[0];
1172 offset.y = data[1];
1173 offset.z = data[2];
1174 printk(KERN_INFO "set calibration finished\n");
1175 return count;
1176 }
1177
SC7660_register_store(struct device * dev,struct device_attribute * attr,const char * buf,size_t count)1178 static ssize_t SC7660_register_store(struct device *dev,
1179 struct device_attribute *attr,
1180 const char *buf, size_t count)
1181 {
1182 int address, value;
1183 int result = 0;
1184 sscanf(buf, "0x%x=0x%x", &address, &value);
1185
1186 result = sensor_write_reg(sc7660_client, address,value);
1187
1188 if(result)
1189 printk("%s:fail to write sensor_register\n",__func__);
1190
1191 return count;
1192 }
1193
SC7660_register_show(struct device * dev,struct device_attribute * attr,char * buf)1194 static ssize_t SC7660_register_show(struct device *dev,
1195 struct device_attribute *attr, char *buf)
1196 {
1197 size_t count = 0;
1198 char i;
1199 char buffer[3] = {0};
1200 i = 0x0f;
1201 *buffer = i;
1202 count = sensor_rx_data(sc7660_client, &buffer[0], 1);
1203 count += sprintf(buf, "0x%x: 0x%x\n", i, buffer[0]);
1204 for(i=0x10;i<0x5a;i++)
1205 {
1206 *buffer = i;
1207
1208 sensor_rx_data(sc7660_client, buffer, 1);
1209 //sensor_rx_data(sc7660_client, &buffer[0], 1);
1210 count += sprintf(&buf[count],"0x%x: 0x%x\n", i, buffer[0]);
1211 }
1212 return count;
1213 }
1214
SC7660_value_show(struct device * dev,struct device_attribute * attr,char * buf)1215 static ssize_t SC7660_value_show(struct device *dev,
1216 struct device_attribute *attr, char *buf)
1217 {
1218 s16 x,y,z;
1219 int ret;
1220 char buffer1[3],buffer2[3] = {0};
1221
1222 memset(buffer1, 0, 3);
1223 memset(buffer2, 0, 3);
1224
1225 *buffer1 = SC7660_STATUS;
1226 ret = sensor_rx_data(sc7660_client, buffer1,1);
1227 buffer1[0] &= 0x08;
1228 if(!buffer1[0])
1229 return sprintf(buf, "SC7660 data is not ready!\n");
1230
1231 *buffer1 = SC7660_XOUT_L;
1232 ret = sensor_rx_data(sc7660_client, buffer1,1);
1233 *buffer2 = SC7660_XOUT_H;
1234 ret = sensor_rx_data(sc7660_client, buffer2,1);
1235 x = (((s16)((buffer2[0] << 8) + buffer1[0])) >>4);
1236
1237 *buffer1 = SC7660_YOUT_L;
1238 ret = sensor_rx_data(sc7660_client, buffer1,1);
1239 *buffer2 = SC7660_YOUT_H;
1240 ret = sensor_rx_data(sc7660_client, buffer2,1);
1241 y = (((s16)((buffer2[0] << 8) + buffer1[0])) >>4);
1242
1243 *buffer1 = SC7660_ZOUT_L;
1244 ret = sensor_rx_data(sc7660_client, buffer1,1);
1245 *buffer2 = SC7660_ZOUT_H;
1246 ret = sensor_rx_data(sc7660_client, buffer2,1);
1247 z = (((s16)((buffer2[0] << 8) + buffer1[0])) >>4);
1248
1249 if (ret < 0)
1250 return sprintf(buf, "SC7660_read_data failed!\n");
1251 else
1252 return sprintf(buf, "x=%4d(0x%4x),y=%4d(0x%4x),z=%4d(0x%4x)\n",x,x,y,y,z,z);
1253
1254 }
1255
1256 static DEVICE_ATTR(reg, 0664,
1257 SC7660_register_show, SC7660_register_store);
1258
1259 static DEVICE_ATTR(calibration_run, 0664, //calibration_run
1260 NULL, SC7660_3_axis_Calibration);
1261 static DEVICE_ATTR(calibration_reset, 0664,
1262 NULL, SC7660_calibration_reset_store);
1263 static DEVICE_ATTR(calibration_value,0664,
1264 SC7660_calibration_value_show,
1265 SC7660_calibration_value_store);
1266 static DEVICE_ATTR(value, 0664,
1267 SC7660_value_show, NULL);
1268
1269 static struct attribute *SC7660_attributes[] = {
1270 &dev_attr_value.attr,
1271 &dev_attr_reg.attr,
1272 &dev_attr_calibration_run.attr,
1273 &dev_attr_calibration_reset.attr,
1274 &dev_attr_calibration_value.attr,
1275 NULL
1276 };
1277
1278 static struct attribute_group SC7660_attribute_group = {
1279 .attrs = SC7660_attributes
1280 };
1281
1282 /****************operate according to sensor chip:start************/
1283
sensor_active(struct i2c_client * client,int enable,int rate)1284 static int sensor_active(struct i2c_client *client, int enable, int rate)
1285 {
1286 struct sensor_private_data *sensor =
1287 (struct sensor_private_data *) i2c_get_clientdata(client);
1288 int result = 0;
1289 int status = 0;
1290
1291 sensor->ops->ctrl_data = 0x07;
1292
1293 //register setting according to chip datasheet
1294 if(enable)
1295 {
1296 status = SC7660_ENABLE; //sc7660
1297 sensor->ops->ctrl_data |= SC7660_400HZ;
1298 }
1299 else
1300 status = ~SC7660_ENABLE; //sc7660
1301
1302 printk("%s:reg=0x%x,reg_ctrl=0x%x,enable=%d\n",__func__,sensor->ops->ctrl_reg, sensor->ops->ctrl_data, enable);
1303 result = sensor_write_reg(client, sensor->ops->ctrl_reg, sensor->ops->ctrl_data);
1304 //sensor_write_reg(client, SC7660_BOOT, 0x80);
1305 if(result)
1306 printk("%s:fail to active sensor\n",__func__);
1307
1308 return result;
1309
1310 }
1311
sensor_init(struct i2c_client * client)1312 static int sensor_init(struct i2c_client *client)
1313 {
1314 struct sensor_private_data *sensor =
1315 (struct sensor_private_data *) i2c_get_clientdata(client);
1316 int result = 0;
1317 int ret;
1318 unsigned char chip_id[3] = {0,0,0};
1319 //char reg_cali;
1320
1321 //mutex_lock(&(sensor->allen_mutex) );//allen
1322
1323 printk("aaaaa %s:line=%d\n",__func__,__LINE__);
1324
1325 result = sensor->ops->active(client,0,0);
1326 if(result)
1327 {
1328 printk("%s:line=%d,error\n",__func__,__LINE__);
1329 return result;
1330 }
1331 sc7660_client = client;
1332 sensor->status_cur = SENSOR_OFF;
1333 //sensor->time_of_cali =0;//allen
1334 offset.x=offset.y=offset.z=0;
1335
1336 *chip_id = 0x0f;
1337 ret = sensor_rx_data(client, chip_id,1);
1338 printk("sc7660_chip_id is %d",chip_id[0]);
1339 sensor_write_reg(client, SC7660_BOOT, 0x80);
1340 mdelay(20);
1341 sensor_write_reg(client, SC7660_MODE3, 0x88);
1342
1343 result = sensor_write_reg(client, SC7660_MODE, 0x07);
1344
1345 //HR mode //sc7660
1346
1347 //register_test();
1348 if(result)
1349 {
1350 printk("aaaaa %s:line=%d,error\n",__func__,__LINE__);
1351 return result;
1352 }
1353
1354
1355
1356 if(sensor->pdata->irq_enable) //open interrupt
1357 {
1358 result = sensor_write_reg(client, SC7660_MODE2, 0x10);
1359 result = sensor_write_reg(client, 0x25, 0x02);
1360
1361 if(result)
1362 {
1363 printk("%s:line=%d,error\n",__func__,__LINE__);
1364 return result;
1365 }
1366 }
1367 memset(&axis_average, 0, sizeof(struct sensor_axis_average));
1368
1369 if(noCreateAttr)
1370 {
1371 struct input_dev* pInputDev;
1372 pInputDev = input_allocate_device();
1373 if (!pInputDev) {
1374 dev_err(&client->dev,
1375 "Failed to allocate input device %s\n", sensor->input_dev->name);
1376 return -ENOMEM;
1377 }
1378
1379 pInputDev->name = "sc7660";
1380 set_bit(EV_ABS, pInputDev->evbit);
1381
1382 /* x-axis acceleration */
1383 input_set_abs_params(pInputDev, ABS_X, sensor->ops->range[0], sensor->ops->range[1], 0, 0);
1384 /* y-axis acceleration */
1385 input_set_abs_params(pInputDev, ABS_Y, sensor->ops->range[0], sensor->ops->range[1], 0, 0);
1386 /* z-axis acceleration */
1387 input_set_abs_params(pInputDev, ABS_Z, sensor->ops->range[0], sensor->ops->range[1], 0, 0);
1388
1389 ret = input_register_device(pInputDev);
1390 if (ret) {
1391 dev_err(&client->dev,
1392 "Unable to register input device %s\n", pInputDev->name);
1393 return -ENOMEM;
1394 }
1395
1396 DBG("Sys Attribute Register here %s is called for DA311.\n", __func__);
1397 ret = sysfs_create_group(&pInputDev->dev.kobj, &SC7660_attribute_group);
1398 if (ret) {
1399 DBG("sc7660 sysfs_create_group Error err=%d..", ret);
1400 ret = -EINVAL;
1401 }
1402
1403 noCreateAttr = 0;
1404 }
1405
1406 return result;
1407 }
1408
1409
sensor_convert_data(struct i2c_client * client,char high_byte,char low_byte,s16 off)1410 static int sensor_convert_data(struct i2c_client *client, char high_byte, char low_byte ,s16 off)
1411 {
1412 s64 result;
1413 result = (((s16)((high_byte << 8) + low_byte)) >>4);
1414 result -= off;
1415 if (result < SC7660_BOUNDARY)
1416 result = result* SC7660_GRAVITY_STEP;
1417 else
1418 result = ~( ((~result & (0x7ffff>>(20-SC7660_PRECISION)) ) + 1)
1419 * SC7660_GRAVITY_STEP) + 1;
1420
1421 return (int)result;
1422 }
1423
1424
gsensor_report_value(struct i2c_client * client,struct sensor_axis * axis)1425 static int gsensor_report_value(struct i2c_client *client, struct sensor_axis *axis)
1426 {
1427 struct sensor_private_data *sensor =
1428 (struct sensor_private_data *) i2c_get_clientdata(client);
1429
1430 /* Report acceleration sensor information */
1431
1432 //8 in -y -x -z 10 in x -y -z
1433
1434 /* RK3326 platform board */
1435 #if defined (CONFIG_BOARD_RK3326_AK47)
1436 input_report_abs(sensor->input_dev, ABS_X,axis->y);
1437 input_report_abs(sensor->input_dev, ABS_Y,axis->x);
1438 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1439 #elif defined (CONFIG_BOARD_RK3326_TH700)
1440 input_report_abs(sensor->input_dev, ABS_X,axis->y);
1441 input_report_abs(sensor->input_dev, ABS_Y,axis->x);
1442 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1443 #elif defined(CONFIG_BOARD_RK3326_TH863B_10)
1444 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1445 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1446 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1447 #elif defined(CONFIG_BOARD_RK3326_TH863B_8)
1448 input_report_abs(sensor->input_dev, ABS_X,axis->y);
1449 input_report_abs(sensor->input_dev, ABS_Y,axis->x);
1450 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1451 #elif defined(CONFIG_BOARD_RK3326_TH863B_7)
1452 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1453 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1454 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1455 #elif defined(CONFIG_BOARD_RK3326_TH863B_V31_7)
1456 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1457 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1458 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1459 #elif defined(CONFIG_BOARD_RK3326_TH1021DN)
1460 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1461 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1462 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1463 #elif defined(CONFIG_BOARD_RK3326_TH1021DN_V20)
1464 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1465 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1466 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1467 #elif defined(CONFIG_BOARD_RK3326_TH7926_7)
1468 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1469 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1470 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1471 #elif defined(CONFIG_BOARD_RK3326_TH7926_9)
1472 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1473 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1474 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1475 #elif defined(CONFIG_BOARD_RK3326_MT1011)
1476 input_report_abs(sensor->input_dev, ABS_X,-axis->y);
1477 input_report_abs(sensor->input_dev, ABS_Y,-axis->x);
1478 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1479 #elif defined(CONFIG_BOARD_RK3326_M1011QR)
1480 input_report_abs(sensor->input_dev, ABS_X,-axis->y);
1481 input_report_abs(sensor->input_dev, ABS_Y,-axis->x);
1482 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1483
1484 /* RK3126C platform board */
1485 #elif defined(CONFIG_BOARD_RK3126C_AK47)
1486 input_report_abs(sensor->input_dev, ABS_X,axis->y);
1487 input_report_abs(sensor->input_dev, ABS_Y,axis->x);
1488 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1489 #elif defined(CONFIG_BOARD_RK3126C_TH1021DN)
1490 input_report_abs(sensor->input_dev, ABS_X,axis->x);
1491 input_report_abs(sensor->input_dev, ABS_Y,-axis->y);
1492 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1493 #elif defined(CONFIG_BOARD_RK3126C_TH863_7)
1494 input_report_abs(sensor->input_dev, ABS_X,-axis->x);
1495 input_report_abs(sensor->input_dev, ABS_Y,axis->y);
1496 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1497 #elif defined(CONFIG_BOARD_RK3126C_TH863_8)
1498 input_report_abs(sensor->input_dev, ABS_X,axis->y);
1499 input_report_abs(sensor->input_dev, ABS_Y,axis->x);
1500 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1501 #elif defined(CONFIG_BOARD_RK3126C_TH98V)
1502 input_report_abs(sensor->input_dev, ABS_X,axis->y);
1503 input_report_abs(sensor->input_dev, ABS_Y,axis->x);
1504 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1505 #else
1506 input_report_abs(sensor->input_dev, ABS_X,-axis->y);
1507 input_report_abs(sensor->input_dev, ABS_Y,-axis->x);
1508 input_report_abs(sensor->input_dev, ABS_Z,-axis->z);
1509 #endif
1510
1511 input_sync(sensor->input_dev);
1512 DBG("Gsensor x==%d y==%d z==%d\n",axis->x,axis->y,axis->z);
1513
1514 return 0;
1515 }
1516
1517 #define GSENSOR_MIN 2
sensor_report_value(struct i2c_client * client)1518 static int sensor_report_value(struct i2c_client *client)
1519 {
1520 struct sensor_private_data *sensor =
1521 (struct sensor_private_data *) i2c_get_clientdata(client);
1522 struct sensor_platform_data *pdata = sensor->pdata;
1523 int ret = 0;
1524 int x,y,z;
1525 struct sensor_axis axis;
1526 char buffer1[3],buffer2[3] = {0};
1527 char value = 0;
1528 //SC7660_load_user_calibration(client);
1529 memset(buffer1, 0, 3);
1530 memset(buffer2, 0, 3);
1531
1532 *buffer1 = SC7660_STATUS;
1533 ret = sensor_rx_data(sc7660_client, buffer1,1);
1534 buffer1[0] &= 0x08;
1535 if(!buffer1[0])
1536 return ret;
1537
1538 *buffer1 = SC7660_XOUT_L;
1539 ret = sensor_rx_data(sc7660_client, buffer1,1);
1540 *buffer2 = SC7660_XOUT_H;
1541 ret = sensor_rx_data(client, buffer2,1);
1542 if (ret < 0)
1543 return ret;
1544 x = sensor_convert_data(sensor->client, buffer2[0], buffer1[0],0); //buffer[1]:high bit
1545
1546 *buffer1 = SC7660_YOUT_L;
1547 ret = sensor_rx_data(sc7660_client, buffer1,1);
1548 *buffer2 = SC7660_YOUT_H;
1549 ret = sensor_rx_data(client, buffer2,1);
1550 if (ret < 0)
1551 return ret;
1552 y = sensor_convert_data(sensor->client, buffer2[0], buffer1[0],0);
1553 *buffer1 = SC7660_ZOUT_L;
1554 ret = sensor_rx_data(sc7660_client, buffer1,1);
1555 *buffer2 = SC7660_ZOUT_H;
1556 ret = sensor_rx_data(client, buffer2,1);
1557 if (ret < 0)
1558 return ret;
1559 z = sensor_convert_data(sensor->client, buffer2[0], buffer1[0],0);
1560
1561 axis.x = (pdata->orientation[0])*x + (pdata->orientation[1])*y + (pdata->orientation[2])*z;
1562 axis.y = (pdata->orientation[3])*x + (pdata->orientation[4])*y + (pdata->orientation[5])*z;
1563 axis.z = (pdata->orientation[6])*x + (pdata->orientation[7])*y + (pdata->orientation[8])*z;
1564
1565 axis_average.x_average += axis.x;
1566 axis_average.y_average += axis.y;
1567 axis_average.z_average += axis.z;
1568 axis_average.count++;
1569
1570 if(axis_average.count >= SC7660_COUNT_AVERAGE)
1571 {
1572 axis.x = axis_average.x_average / axis_average.count;
1573 axis.y = axis_average.y_average / axis_average.count;
1574 axis.z = axis_average.z_average / axis_average.count;
1575
1576 DBG( "%s: axis = %d %d %d \n", __func__, axis.x, axis.y, axis.z);
1577
1578 memset(&axis_average, 0, sizeof(struct sensor_axis_average));
1579
1580 //Report event only while value is changed to save some power
1581 if((abs(sensor->axis.x - axis.x) > GSENSOR_MIN) || (abs(sensor->axis.y - axis.y) > GSENSOR_MIN) || (abs(sensor->axis.z - axis.z) > GSENSOR_MIN))
1582 {
1583 gsensor_report_value(client, &axis);
1584
1585 /* \BB\A5\B3\E2\B5ػ\BA\B4\E6\CA\FD\BE\DD. */
1586 mutex_lock(&(sensor->data_mutex) );
1587 sensor->axis = axis;
1588 mutex_unlock(&(sensor->data_mutex) );
1589 }
1590 }
1591
1592 if((sensor->pdata->irq_enable)&& (sensor->ops->int_status_reg >= 0)) //read sensor intterupt status register
1593 {
1594
1595 value = sensor_read_reg(client, sensor->ops->int_status_reg);
1596 DBG("%s:sensor int status :0x%x\n",__func__,value);
1597 }
1598
1599 return ret;
1600 }
1601
1602
1603 static struct sensor_operate gsensor_sc7660_ops = {
1604 .name = "gs_sc7660",
1605 .type = SENSOR_TYPE_ACCEL, //sensor type and it should be correct
1606 .id_i2c = ACCEL_ID_SC7660, //i2c id number
1607 .read_reg = SC7660_XOUT_H, //read data
1608 .read_len = 1, //data length
1609 .id_reg = SENSOR_UNKNOW_DATA, //read device id from this register
1610 .id_data = SENSOR_UNKNOW_DATA, //device id
1611 .precision = SC7660_PRECISION, //12 bit
1612 .ctrl_reg = SC7660_MODE, //enable or disable SC7660_MODE
1613 .int_status_reg = SENSOR_UNKNOW_DATA, //intterupt status register
1614 .range = {-SC7660_RANGE,SC7660_RANGE}, //range
1615 .trig = IRQF_TRIGGER_HIGH|IRQF_ONESHOT,
1616 .active = sensor_active,
1617 .init = sensor_init,
1618 .report = sensor_report_value,
1619 };
1620
1621 /****************operate according to sensor chip:end************/
gsensor_sc7660_probe(struct i2c_client * client,const struct i2c_device_id * devid)1622 static int gsensor_sc7660_probe(struct i2c_client *client,
1623 const struct i2c_device_id *devid)
1624 {
1625 return sensor_register_device(client, NULL, devid, &gsensor_sc7660_ops);
1626 }
1627
gsensor_sc7660_remove(struct i2c_client * client)1628 static int gsensor_sc7660_remove(struct i2c_client *client)
1629 {
1630 return sensor_unregister_device(client, NULL, &gsensor_sc7660_ops);
1631 }
1632
1633 static const struct i2c_device_id gsensor_sc7660_id[] = {
1634 {"gs_sc7660", ACCEL_ID_SC7660},
1635 {}
1636 };
1637
1638 static struct i2c_driver gsensor_sc7660_driver = {
1639 .probe = gsensor_sc7660_probe,
1640 .remove = gsensor_sc7660_remove,
1641 .shutdown = sensor_shutdown,
1642 .id_table = gsensor_sc7660_id,
1643 .driver = {
1644 .name = "gsensor_sc7660",
1645 #ifdef CONFIG_PM
1646 .pm = &sensor_pm_ops,
1647 #endif
1648 },
1649 };
1650
1651 module_i2c_driver(gsensor_sc7660_driver);
1652
1653 MODULE_AUTHOR("luowei <lw@rock-chips.com>");
1654 MODULE_DESCRIPTION("sc7660 3-Axis accelerometer driver");
1655 MODULE_LICENSE("GPL");
1656