Takashi Matsuoka / MjSi47xx
Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers MjSi47xx.cpp Source File

MjSi47xx.cpp

00001 #include "MjSi47xx.h"
00002 
00003 MjSi47xx::MjSi47xx(I2C* i2c, uint8_t address, DigitalOut* rst_n)
00004 {
00005     this->i2c = i2c;
00006     this->address = address;
00007     this->rst_n = rst_n;
00008 
00009     reset();
00010 }
00011 
00012 void MjSi47xx::reset()
00013 {
00014     *rst_n = 0;
00015 }
00016 
00017 bool MjSi47xx::powerUp(FunctionType func)
00018 {
00019     switch (func) {
00020         case FUNCTION_FM:
00021         case FUNCTION_AM:
00022             break;
00023         default:
00024             return false;
00025     }
00026 
00027     if (!*rst_n) {
00028         wait_us(250);
00029         *rst_n = 1;
00030         wait_us(1);
00031     }
00032 
00033     uint8_t arg[2];
00034     switch (func) {
00035         case FUNCTION_FM:
00036             arg[0] = 0x10;  // FM Receive
00037             arg[1] = 0x05;  // Analog Out
00038             break;
00039         case FUNCTION_AM:
00040             arg[0] = 0x11;  // AM/SW/LW Receive
00041             arg[1] = 0x05;  // Analog Out
00042             break;
00043     }
00044 
00045     writeCmd(0x01, arg, sizeof (arg));      // POWER_UP
00046     uint8_t status;
00047     readRes(&status);
00048 
00049     return true;
00050 }
00051 
00052 bool MjSi47xx::setProperty(PropertyType property, uint16_t value)
00053 {
00054     const uint8_t arg[] = { 0x00, property / 0x100, property % 0x100, value / 0x100, value % 0x100, };
00055 
00056     writeCmd(0x12, arg, sizeof (arg));  // SET_PROPERTY
00057     uint8_t status;
00058     readRes(&status);
00059 
00060     return true;
00061 }
00062 
00063 bool MjSi47xx::getIntStatus(bool* stcInt)
00064 {
00065     if (stcInt == NULL) return false;
00066 
00067     writeCmd(0x14); // GET_INT_STATUS
00068     uint8_t status;
00069     readRes(&status);
00070 
00071     if (stcInt != NULL) *stcInt = status & 0x01 ? true : false;
00072 
00073     return true;
00074 }
00075 
00076 bool MjSi47xx::fmTuneFrequency(float frequency)
00077 {
00078     if (frequency < 64.0f || 108.0f < frequency) return false;
00079 
00080     int freqInt = (int)(frequency * 100.0f);
00081     const uint8_t arg[] = { 0x00, freqInt / 0x100, freqInt % 0x100, 0x00, };
00082 
00083     writeCmd(0x20, arg, sizeof (arg));  // FM_TUNE_FREQ
00084     uint8_t status;
00085     readRes(&status);
00086 
00087     return true;
00088 }
00089 
00090 bool MjSi47xx::fmTuneStatus(float* frequency, uint8_t* rssi, uint8_t* snr, uint8_t* multipath)
00091 {
00092     const uint8_t arg[] = { 0x01, };
00093 
00094     writeCmd(0x22, arg, sizeof (arg));  // FM_TUNE_STATUS
00095     uint8_t status;
00096     uint8_t resp[7];
00097     readRes(&status, resp, sizeof (resp));
00098 
00099     if (frequency != NULL) *frequency = (float)((int)resp[1] * 0x100 + (int)resp[2]) / 100.0f;
00100     if (rssi != NULL) *rssi = resp[3];
00101     if (snr != NULL) *snr = resp[4];
00102     if (multipath != NULL) *multipath = resp[5];
00103 
00104     return true;
00105 }
00106 
00107 bool MjSi47xx::amTuneFrequency(float frequency)
00108 {
00109     if (frequency < 149.0f || 23000.0f < frequency) return false;
00110 
00111     int freqInt = (int)frequency;
00112     const uint8_t arg[] = { 0x00, freqInt / 0x100, freqInt % 0x100, 0x00, 0x00, };
00113 
00114     writeCmd(0x40, arg, sizeof (arg));  // AM_TUNE_FREQ
00115     uint8_t status;
00116     readRes(&status);
00117 
00118     return true;
00119 }
00120 
00121 bool MjSi47xx::amTuneStatus(float* frequency, uint8_t* rssi, uint8_t* snr)
00122 {
00123     const uint8_t arg[] = { 0x01, };
00124     writeCmd(0x42, arg, sizeof (arg));  // AM_TUNE_STATUS
00125     uint8_t status;
00126     uint8_t resp[7];
00127     readRes(&status, resp, sizeof (resp));
00128 
00129     if (frequency != NULL) *frequency = (float)((int)resp[1] * 0x100 + (int)resp[2]);
00130     if (rssi != NULL) *rssi = resp[3];
00131     if (snr != NULL) *snr = resp[4];
00132 
00133     return true;
00134 }
00135 
00136 void MjSi47xx::writeCmd(uint8_t cmd, const uint8_t* argv, size_t argc)
00137 {
00138     i2c->start();
00139     i2c->write(address);
00140     i2c->write(cmd);
00141     while (argc--) {
00142         i2c->write(*argv++);
00143     }
00144     i2c->stop();
00145 }
00146 
00147 void MjSi47xx::readRes(uint8_t* status, uint8_t *resv, size_t resc)
00148 {
00149     // Wait for CTS. (command has been accepted.)
00150     do {
00151         i2c->start();
00152         i2c->write(address | 1);
00153         *status = i2c->read(0);
00154         i2c->stop();
00155     } while (!(*status & 0x80));
00156 
00157     // ERR?
00158     if (*status & 0x40) {
00159         if (resv != NULL && resc >= 1) {
00160             memset(resv, 0, resc);
00161         }
00162         return;
00163     }
00164 
00165     // Receive response.
00166     i2c->start();
00167     i2c->write(address | 1);
00168     *status = i2c->read(resc >= 1 ? 1 : 0);
00169     while (resc--) {
00170         *resv++ = i2c->read(resc >= 1 ? 1 : 0);
00171     }
00172     i2c->stop();
00173 }
00174 
00175