packages/web/353/php_top/i2c.inc

Go to the documentation of this file.
00001 <?php
00002 /*!***************************************************************************
00003 *! FILE NAME  : i2c.inc
00004 *! DESCRIPTION: Provides functions to read/write over i2c buses in the camera,
00005 *!              low-level R/W and additionally:
00006 *!              Setting per-slave protection mask,
00007 *!              Synchronizing system clock with a "CMOS" one
00008 *!              Reading from/writing to EEPROM memory
00009 *! Copyright (C) 2008 Elphel, Inc
00010 *! -----------------------------------------------------------------------------**
00011 *!
00012 *!  This program is free software: you can redistribute it and/or modify
00013 *!  it under the terms of the GNU General Public License as published by
00014 *!  the Free Software Foundation, either version 3 of the License, or
00015 *!  (at your option) any later version.
00016 *!
00017 *!  This program is distributed in the hope that it will be useful,
00018 *!  but WITHOUT ANY WARRANTY; without even the implied warranty of
00019 *!  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00020 *!  GNU General Public License for more details.
00021 *!
00022 *!  You should have received a copy of the GNU General Public License
00023 *!  along with this program.  If not, see <http://www.gnu.org/licenses/>.
00024 *! -----------------------------------------------------------------------------**
00025 *!  $Log: i2c.inc,v $
00026 *!  Revision 1.3  2008/07/16 23:18:54  spectr_rain
00027 *!  option cmd=readCMOS - just read w/o modification of camera time
00028 *!
00029 *!  Revision 1.2  2008/03/16 01:24:09  elphel
00030 *!  Added i2c speed control interface
00031 *!
00032 *!  Revision 1.1  2008/03/15 23:05:18  elphel
00033 *!  split i2c.php into i2c.php and i2c.inc (to be used from other scripts)
00034 *!
00035 *!
00036 */
00037 
00038 function i2c_ctl($bus,$data="") { 
00039    $size=6; // bytes per bus
00040    $data=trim($data);
00041    if ($data!="") {
00042      $darr=explode(":",$data);
00043      $i2cctl  = fopen('/dev/xi2cctl', 'w');
00044      for ($i=0; ($i<$size) && ($i<count($darr)); $i++) if ($darr[$i]!=""){
00045        fseek ($i2cctl, $bus*$size+$i) ;
00046        fwrite($i2cctl, chr($darr[$i]+0), 1);
00047      }
00048      fclose($i2cctl);
00049    }
00050    $i2cctl  = fopen('/dev/xi2cctl', 'r');
00051    fseek ($i2cctl, $bus*$size) ;
00052    $data = fread($i2cctl, $size);
00053    fclose($i2cctl);
00054    $xml = new SimpleXMLElement("<?xml version='1.0'?><i2cctl/>");
00055            $xml->addChild ('scl_high',ord($data[0]));
00056            $xml->addChild ('scl_low', ord($data[1]));
00057            $xml->addChild ('slave2master', ord($data[2]));
00058            $xml->addChild ('master2slave', ord($data[3]));
00059            $xml->addChild ('filter_sda',   ord($data[4]));
00060            $xml->addChild ('filter_scl',   ord($data[5]));
00061 //           $data=$xml->asXML();
00062    return $xml;
00063 
00064 } // end of i2c_ctl()
00065 
00066 function i2c_send($width,$bus,$a,$d,$raw=0) { //$a<0 - use raw read/write
00067    $w=($width==16)?2:1;
00068    $i2c_fn='/dev/xi2c'.($raw?'raw':(($w==2)?'16':'8')).(($bus==0)?'':'_aux');
00069    $i2c  = fopen($i2c_fn, 'w');
00070    fseek ($i2c, $w*$a) ;
00071    if ($w==1)    $res=fwrite($i2c, chr ($d));
00072    else          $res=fwrite($i2c, chr (floor($d/256)).chr ($d-256*floor($d/256)));
00073    fclose($i2c);
00074    return $res;
00075 } // end of i2c_send()
00076 
00077 function i2c_receive($width,$bus,$a,$raw=0) {
00078    $w=($width==16)?2:1;
00079    $i2c_fn='/dev/xi2c'.($raw?'raw':(($w==2)?'16':'8')).(($bus==0)?'':'_aux');
00080    $i2c  = fopen($i2c_fn, 'r');
00081    fseek ($i2c, $w*$a) ;
00082    $data = fread($i2c, $w);
00083    fclose($i2c);
00084    if (strlen($data)<$w) return -1;
00085    $v=unpack(($w==1)?'C':'n1',$data);
00086    return $v[1];
00087 } // end of i2c_receive()
00088 
00089 function i2c_setprot ($bus,$slave,$bit,$value) { 
00090    $i2cprot  = fopen("/dev/xi2cenable", 'r+');
00091    fseek ($i2cprot,($bus*128)+($slave>>1));
00092    $data=ord(fread($i2cprot,1));
00093    if ($value) $data |= (1<<$bit);
00094    else $data &= ~(1<<$bit);
00095    fseek ($i2cprot,($bus*128)+($slave>>1));
00096    fwrite($i2cprot, chr ($data));
00097    fclose($i2cprot);
00098 } // end of i2c_setprot ()
00099 
00100 function i2c_getCMOSClock(){
00101    $i2c  = fopen('/dev/xi2c8_aux', 'r');
00102    fseek ($i2c, 0x5102) ; //seconds in clock on the 10369 board
00103    $data = fread($i2c, 7); //sec/min/hours/days/weekdays/century-months/years, BCD
00104    fclose($i2c);
00105    if (strlen($data)<7) return "error";
00106    $v=unpack('C*',$data);
00107    $d=array("sec"  =>($v[1]& 0xf)+ 10* (($v[1]>>4)& 0x7),
00108             "min"  =>($v[2]& 0xf)+ 10* (($v[2]>>4)& 0x7),
00109             "hrs"  =>($v[3]& 0xf)+ 10* (($v[3]>>4)& 0x3),
00110             "day"  =>($v[4]& 0xf)+ 10* (($v[4]>>4)& 0x3),
00111             "wday" => $v[5]& 0x7,
00112             "month"=>($v[6]& 0xf)+ 10* (($v[6]>>4)& 0x1),
00113             "year" =>($v[7]& 0xf)+ 10* (($v[7]>>4)& 0xf) + (($v[6] & 0x80)?2000:1900)
00114            );
00115    exec("date -s ".sprintf("%02d%02d%02d%02d%04d.%02d",$d["month"],$d["day"],$d["hrs"],$d["min"],$d["year"],$d["sec"]),$out,$ret);
00116    return $ret;
00117 } // end of i2c_getCMOSClock()
00118 
00119 function i2c_readCMOSClock(){
00120    $i2c  = fopen('/dev/xi2c8_aux', 'r');
00121    fseek ($i2c, 0x5102) ; //seconds in clock on the 10369 board
00122    $data = fread($i2c, 7); //sec/min/hours/days/weekdays/century-months/years, BCD
00123    fclose($i2c);
00124    if (strlen($data)<7) return "error";
00125    $v=unpack('C*',$data);
00126    $d=array("sec"  =>($v[1]& 0xf)+ 10* (($v[1]>>4)& 0x7),
00127             "min"  =>($v[2]& 0xf)+ 10* (($v[2]>>4)& 0x7),
00128             "hrs"  =>($v[3]& 0xf)+ 10* (($v[3]>>4)& 0x3),
00129             "day"  =>($v[4]& 0xf)+ 10* (($v[4]>>4)& 0x3),
00130             "wday" => $v[5]& 0x7,
00131             "month"=>($v[6]& 0xf)+ 10* (($v[6]>>4)& 0x1),
00132             "year" =>($v[7]& 0xf)+ 10* (($v[7]>>4)& 0xf) + (($v[6] & 0x80)?2000:1900)
00133            );
00134 //   exec("date -s ".sprintf("%02d%02d%02d%02d%04d.%02d",$d["month"],$d["day"],$d["hrs"],$d["min"],$d["year"],$d["sec"]),$out,$ret);
00135    return $ret;
00136 } // end of i2c_readCMOSClock()
00137 
00138 function i2c_bcd($v) {
00139   $d=intval($v,10);
00140   return $d + 6*floor($d/10);
00141 } // end of i2c_bcd($v)
00142 
00143 function i2c_setCMOSClock(){
00144  $ts=time();
00145  $data=chr(i2c_bcd(gmdate("s",$ts))).
00146        chr(i2c_bcd(gmdate("i",$ts))).
00147        chr(i2c_bcd(gmdate("H",$ts))).
00148        chr(i2c_bcd(gmdate("d",$ts))).
00149        chr(i2c_bcd(gmdate("w",$ts))).
00150        chr(i2c_bcd(gmdate("m",$ts))+ ((intval(gmdate("Y",$ts),10)>=2000)?0x80:0)).
00151        chr(i2c_bcd(gmdate("y",$ts)));
00152    $i2c  = fopen('/dev/xi2c8_aux', 'w');
00153    fseek ($i2c, 0x5102) ; //seconds in clock on the 10369 board
00154    $written= fwrite($i2c, $data);
00155    fclose($i2c);
00156    if ($written < strlen($data)) return "error";
00157    return "OK";
00158 } // end of i2c_setCMOSClock()
00159 
00160 function i2c_read256b($slave=0xa0) { //will read 256 bytes from slave (address is 8-bit, includes r/~w)
00161    $i2c  = fopen('/dev/xi2c8_aux', 'r');
00162    fseek ($i2c, $slave*128) ; //256 per slave, but slave are only even
00163    $data = fread($i2c, 256);  // full 256 bytes
00164    fclose($i2c);
00165    return $data;
00166 } // end of i2c_read256b ()
00167 
00168 //this EEPROM writes only 4 bytes sequentionally (only 2 LSBs are incremented)
00169 function i2c_write256b($data, $slave=0xa0) { //will write up to 256 bytes $data to slave (address is 8-bit, includes r/~w). EEPROM should be un-protected
00170    $maxretries=200; //measured - 19
00171    if (!is_string($data)) return -1;
00172    if (strlen($data)>256) return -2;
00173    if (strlen($data)<256) $data.=chr(0);
00174    $i2c  = fopen('/dev/xi2c8_aux', 'w');
00175    $len=0;
00176    for ($i=0;$i<strlen($data); $i+=4) {
00177      for ($retry=0; $retry< $maxretries; $retry++) {
00178        fseek ($i2c, $slave*128+$i) ; //256 per slave, but slave are only even
00179        $rslt=fwrite($i2c, substr($data,$i,4));
00180        if ($rslt>0) break;
00181      }
00182      if ($rslt<=0) {
00183       $len=$rslt;
00184       break;
00185      }
00186      $len+=$rslt;
00187    }
00188    fclose($i2c);
00189    return $len;
00190 } // end of i2c_write256b ()
00191 ?>

Generated on Thu Aug 7 16:19:01 2008 for elphel by  doxygen 1.5.1