00001 #include "edtinc.h"
00002
00003 #include "lib_adt7461.h"
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 void
00014 edt_adt7461_set_reg(EdtDev *edt_p, u_int adt7461_reg)
00015 {
00016 edt_p->adt7461_reg = (u_int) adt7461_reg;
00017 }
00018
00019 u_int
00020 edt_adt7461_get_reg(EdtDev *edt_p)
00021 {
00022 if (edt_p->adt7461_reg == 0)
00023 edt_p->adt7461_reg = (u_int) EDT_ADT7461_REG;
00024
00025 return (u_int) edt_p->adt7461_reg;
00026 }
00027
00028
00029 void edt_adt7461_set_mezzanine_chip(EdtDev *edt_p, int mezzanine_chip_select)
00030 {
00031 switch (mezzanine_chip_select)
00032 {
00033 case 0:
00034 edt_p->adt7461_reg = (u_int) EDT_ADT7461_MEZZ0_REG;
00035 break;
00036
00037 case 1:
00038 edt_p->adt7461_reg = (u_int) EDT_ADT7461_MEZZ1_REG;
00039 break;
00040
00041 default:
00042 edt_p->adt7461_reg = (u_int) EDT_ADT7461_REG;
00043 }
00044 }
00045
00046
00047 void edt_adt7461_set_baseboard_chip(EdtDev *edt_p, int baseboard_chip_select)
00048 {
00049
00050 edt_p->adt7461_reg = (u_int) EDT_ADT7461_REG;
00051
00052 if (baseboard_chip_select == 1)
00053 edt_reg_or(edt_p, EDT_PCIE_CFG, 1);
00054 else
00055 edt_reg_and(edt_p, EDT_PCIE_CFG, 0xFFFFFFE);
00056
00057 }
00058
00059 void
00060 edt_adt7461_set_clock(EdtDev *edt_p, int clock)
00061 {
00062 int val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & ~EDT_ADT7461_CLK;
00063 edt_reg_write(edt_p, (u_int)edt_p->adt7461_reg, (val | ((clock)?EDT_ADT7461_CLK:0)));
00064 }
00065
00066 void
00067 edt_adt7461_set_data(EdtDev *edt_p, int data)
00068 {
00069 int val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & ~EDT_ADT7461_DATA;
00070 edt_reg_write(edt_p, (u_int)edt_p->adt7461_reg, (val | ((data)?EDT_ADT7461_DATA:0)));
00071 }
00072
00073 void
00074 edt_adt7461_set_den(EdtDev *edt_p, int enable)
00075 {
00076 int val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & ~EDT_ADT7461_TRISTATE;
00077 edt_reg_write(edt_p, (u_int)edt_p->adt7461_reg, (val | ((!enable)?EDT_ADT7461_TRISTATE:0)));
00078 }
00079
00080 void
00081 edt_adt7461_show_bits(EdtDev *edt_p)
00082
00083 {
00084 int val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg);
00085
00086 printf("%s %s %s\n",
00087 (val & EDT_ADT7461_TRISTATE)? "DEN":" ",
00088 (val & EDT_ADT7461_DATA)?"DATA":" ",
00089 (val & EDT_ADT7461_CLK)?"CLK":" ");
00090
00091 }
00092
00093 void
00094 edt_adt7461_set(EdtDev *edt_p, int enable, int data, int clock )
00095 {
00096 int rval = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) &
00097 ~(EDT_ADT7461_TRISTATE|EDT_ADT7461_CLK|EDT_ADT7461_DATA) ;
00098
00099 int val = ((clock) ? EDT_ADT7461_CLK : 0)
00100 | ((data) ? EDT_ADT7461_DATA : 0) | ((enable) ? 0 : EDT_ADT7461_TRISTATE);
00101
00102
00103 edt_reg_write(edt_p, (u_int)edt_p->adt7461_reg, val | rval);
00104
00105
00106
00107
00108
00109 }
00110
00111
00112 int
00113 edt_adt7461_get_therm_reset(EdtDev *edt_p)
00114
00115 {
00116 int val;
00117 val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & EDT_ADT7461_THERM_RESET;
00118 return (val != 0);
00119 }
00120
00121 void
00122 edt_adt7461_set_therm_reset(EdtDev *edt_p, int enable)
00123
00124 {
00125 int val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & ~EDT_ADT7461_THERM_RESET;
00126 edt_reg_write(edt_p, (u_int)edt_p->adt7461_reg, val | (enable)?EDT_ADT7461_THERM_RESET:0);
00127 }
00128
00129 int
00130 edt_adt7461_read_alert_pin(EdtDev *edt_p)
00131 {
00132 if ((edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & EDT_ADT7461_ALERT) != 0) {
00133 return 1;
00134 } else {
00135 return 0;
00136 }
00137 }
00138
00139
00140 int
00141 edt_adt7461_read_data_pin(EdtDev *edt_p)
00142 {
00143 int val;
00144 val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & EDT_ADT7461_DATA;
00145 edt_msg(EDTLIB_MSG_INFO_2, "read_data_pin %x\n", val);
00146 return (val != 0);
00147 }
00148
00149 int
00150 edt_adt7461_read_therm_pin(EdtDev *edt_p)
00151 {
00152 int val;
00153 val = edt_reg_read(edt_p, (u_int)edt_p->adt7461_reg) & EDT_ADT7461_THERM;
00154 edt_msg(EDTLIB_MSG_INFO_2, "read_data_pin %x\n", val);
00155 return (val != 0);
00156 }
00157
00158
00159
00160
00161
00162 void
00163 edt_adt7461_send_bus_reset(EdtDev *edt_p)
00164 {
00165
00166 edt_msg(EDTLIB_MSG_INFO_2, "Send Bus Reset\n");
00167 edt_adt7461_set_den(edt_p, 1);
00168 edt_adt7461_set_clock(edt_p,1);
00169 edt_adt7461_set_data(edt_p,1);
00170 edt_adt7461_set_data(edt_p,0);
00171
00172
00173
00174 }
00175
00176 void
00177 edt_adt7461_send_bus_start(EdtDev *edt_p)
00178
00179 {
00180
00181
00182 edt_msg(EDTLIB_MSG_INFO_2, "Send Bus Start\n");
00183
00184
00185 edt_adt7461_set_den(edt_p,1);
00186 edt_adt7461_set_data(edt_p,1);
00187
00188 edt_adt7461_set_data(edt_p,0);
00189
00190 edt_adt7461_set_clock(edt_p,0);
00191
00192
00193
00194 }
00195
00196 void
00197 edt_adt7461_send_bus_stop(EdtDev *edt_p)
00198
00199 {
00200
00201
00202 edt_msg(EDTLIB_MSG_INFO_2, "Send Bus Stop\n");
00203 edt_adt7461_set_clock(edt_p,1);
00204
00205 edt_adt7461_set_data(edt_p,0);
00206 edt_adt7461_set_data(edt_p,1);
00207
00208
00209 }
00210
00211 int
00212 edt_adt7461_get_ack(EdtDev *edt_p)
00213
00214 {
00215 int rc = 1;
00216 edt_msg(EDTLIB_MSG_INFO_2, "Get Ack\n");
00217
00218
00219 edt_adt7461_set_den(edt_p,0);
00220 edt_adt7461_set_clock(edt_p, 0);
00221 edt_adt7461_set_clock(edt_p, 1);
00222
00223
00224
00225
00226 if (edt_adt7461_read_data_pin(edt_p)) {
00227 rc = 0;
00228 }
00229
00230 edt_adt7461_set_clock(edt_p, 0);
00231
00232
00233
00234 return rc;
00235 }
00236
00237
00238 int
00239 edt_adt7461_send_data_byte(EdtDev *edt_p, int data)
00240
00241 {
00242
00243 int i;
00244
00245 int dbit;
00246 edt_msg(EDTLIB_MSG_INFO_2, "Send Data Byte %02x\n", data);
00247
00248 edt_adt7461_set_den(edt_p, 1);
00249 edt_adt7461_set_clock(edt_p, 0);
00250
00251 for (i = 0; i < 8; i++) {
00252 dbit = data & 0x80;
00253 edt_adt7461_set_data(edt_p, dbit);;
00254 edt_adt7461_set_clock(edt_p, 1);
00255 edt_adt7461_set_clock(edt_p, 0);
00256
00257 data = data << 1;
00258 }
00259
00260 if (!edt_adt7461_get_ack(edt_p))
00261 return -1;
00262
00263 return 0;
00264 }
00265
00266 int
00267 edt_adt7461_get_data_byte(EdtDev *edt_p, int doAcknowledge)
00268
00269 {
00270
00271 int i;
00272 int data = 0;
00273
00274 edt_msg(EDTLIB_MSG_INFO_2, "Get Data Byte %s\n", (doAcknowledge)?"Ack" : "");
00275
00276 edt_adt7461_set_den(edt_p,0);
00277 edt_adt7461_set_clock(edt_p, 0);
00278
00279 for (i = 0; i < 8; i++) {
00280 edt_adt7461_set_clock(edt_p,1);
00281 data = (data << 1) | ( edt_adt7461_read_data_pin(edt_p) ? 0x01 : 0x00 );
00282 edt_adt7461_set_clock(edt_p,0);
00283 }
00284 if (doAcknowledge) {
00285
00286 if (!edt_adt7461_get_ack(edt_p))
00287 return -1;
00288 else
00289 return data;
00290 } else {
00291 edt_adt7461_set_den(edt_p,1);
00292 edt_adt7461_set_data(edt_p, 1);
00293
00294 edt_adt7461_set_clock(edt_p,1);
00295 edt_adt7461_set_clock(edt_p,0);
00296
00297 return data;
00298 }
00299 }
00300
00301
00302
00303
00304
00305 int
00306 edt_adt7461_reg_read(EdtDev *edt_p, int address)
00307
00308 {
00309 int status;
00310 int data;
00311 switch (0) {
00312 case 0:
00313
00314 edt_adt7461_send_bus_start(edt_p);
00315
00316 status = edt_adt7461_send_data_byte(edt_p, (EDT_ADT7461_DEVICE_ADDR << 1) | 0x00);
00317 if (status == -1) break;
00318
00319 status = edt_adt7461_send_data_byte(edt_p, address);
00320 if (status == -1) break;
00321
00322 edt_adt7461_send_bus_stop(edt_p);
00323
00324 edt_adt7461_send_bus_start(edt_p);
00325
00326 status = edt_adt7461_send_data_byte(edt_p, (EDT_ADT7461_DEVICE_ADDR << 1) | 0x01);
00327 if (status == -1) break;
00328
00329 data = edt_adt7461_get_data_byte(edt_p, 0);
00330 if (data == -1) break;
00331
00332 edt_adt7461_send_bus_stop(edt_p);
00333 return data;
00334 }
00335
00336 edt_adt7461_send_bus_reset(edt_p);
00337 return -1;
00338 }
00339
00340 int
00341 edt_adt7461_reg_write(EdtDev *edt_p, int address, int data)
00342
00343 {
00344 int status;
00345 switch (0) {
00346 case 0:
00347
00348 edt_adt7461_send_bus_start(edt_p);
00349
00350 status = edt_adt7461_send_data_byte(edt_p, (EDT_ADT7461_DEVICE_ADDR << 1) | 0x00);
00351 if (status == -1) break;
00352
00353 status = edt_adt7461_send_data_byte(edt_p, address);
00354 if (status == -1) break;
00355
00356 status = edt_adt7461_send_data_byte(edt_p, data);
00357 if (status == -1) break;
00358
00359 edt_adt7461_send_bus_stop(edt_p);
00360 return 0;
00361 }
00362
00363 edt_adt7461_send_bus_reset(edt_p);
00364 return -1;
00365 }
00366
00367 int
00368 edt_adt7461_read_alert_address(EdtDev *edt_p)
00369
00370 {
00371 int status;
00372 int deviceAddress;
00373 switch (0) {
00374 case 0:
00375
00376 edt_adt7461_send_bus_start(edt_p);
00377
00378 status = edt_adt7461_send_data_byte(edt_p, (EDT_ADT7461_ALERT_RESPONSE_ADDR << 1) | 0x01);
00379 if (status == -1) break;
00380
00381 deviceAddress = edt_adt7461_get_data_byte(edt_p, 0);
00382 if (deviceAddress == -1) break;
00383
00384 edt_adt7461_send_bus_stop(edt_p);
00385 return deviceAddress & 0xFE;
00386 }
00387
00388 edt_adt7461_send_bus_reset(edt_p);
00389 return -1;
00390 }
00391
00392
00393
00394
00395
00396
00397
00398 int
00399 edt_adt7461_read_extern(EdtDev *edt_p, int tenbits)
00400
00401 {
00402
00403 int low, high;
00404
00405 low = edt_adt7461_reg_read(edt_p,EDT_ADT7461_EXT_TEMP_LOW_BYTE_R);
00406 high = edt_adt7461_reg_read(edt_p,EDT_ADT7461_EXT_TEMP_R);
00407
00408 if (tenbits)
00409 return (high << 2) | (low >> 6);
00410 else
00411 return high;
00412 }
00413
00414 int
00415 edt_adt7461_read_intern(EdtDev *edt_p)
00416
00417 {
00418 return edt_adt7461_reg_read(edt_p,EDT_ADT7461_INTERN_TEMP_R);
00419 }
00420
00421 void
00422 edt_adt7461_set_alert_high(EdtDev *edt_p, int alert_high)
00423
00424 {
00425 edt_adt7461_reg_write(edt_p, EDT_ADT7461_EXT_TEMP_HIGH_W, alert_high);
00426 }
00427
00428 int
00429 edt_adt7461_get_alert_high(EdtDev *edt_p)
00430
00431 {
00432 return edt_adt7461_reg_read(edt_p, EDT_ADT7461_EXT_TEMP_HIGH_R);
00433 }
00434 void
00435 edt_adt7461_set_alert_low(EdtDev *edt_p, int alert_low)
00436
00437 {
00438 edt_adt7461_reg_write(edt_p, EDT_ADT7461_EXT_TEMP_LOW_W, alert_low);
00439 }
00440
00441 int
00442 edt_adt7461_get_alert_low(EdtDev *edt_p)
00443
00444 {
00445 return edt_adt7461_reg_read(edt_p, EDT_ADT7461_EXT_TEMP_LOW_R);
00446 }
00447
00448 void
00449 edt_adt7461_set_therm(EdtDev *edt_p, int therm_high)
00450
00451 {
00452
00453 edt_adt7461_reg_write(edt_p, EDT_ADT7461_EXT_THERM_W, therm_high);
00454
00455
00456 }
00457
00458 int
00459 edt_adt7461_get_therm(EdtDev *edt_p)
00460
00461 {
00462
00463 return edt_adt7461_reg_read(edt_p, EDT_ADT7461_EXT_THERM_W);
00464
00465
00466 }
00467
00468 void
00469 edt_adt7461_set_therm_hysteresis(EdtDev *edt_p, int hysteresis)
00470
00471 {
00472
00473 edt_adt7461_reg_write(edt_p, EDT_ADT7461_THERM_HYSTERESIS, hysteresis);
00474
00475 }
00476
00477 int
00478 edt_adt7461_get_therm_hysteresis(EdtDev *edt_p)
00479
00480 {
00481
00482 return edt_adt7461_reg_read(edt_p, EDT_ADT7461_THERM_HYSTERESIS);
00483
00484 }
00485
00486 int
00487 edt_adt7461_get_alert(EdtDev *edt_p)
00488
00489 {
00490 int alert;
00491
00492 alert = edt_adt7461_read_alert_pin(edt_p);
00493
00494
00495
00496 if (alert)
00497 edt_adt7461_read_alert_address(edt_p);
00498
00499 return alert;
00500 }
00501
00502 void
00503 edt_adt4761_print_status(EdtDev *edt_p, int full)
00504
00505 {
00506
00507 int alert;
00508 int external;
00509 int internal;
00510 int therm;
00511
00512
00513 alert = edt_adt7461_get_alert(edt_p);
00514 therm = edt_adt7461_read_therm_pin(edt_p);
00515 external = edt_adt7461_read_extern(edt_p, TRUE);
00516 internal = edt_adt7461_read_intern(edt_p);
00517 printf("Ext %d.%02d Int %i", external >> 2, (external & 3) * 25, internal);
00518
00519 if (full)
00520 {
00521
00522
00523 printf(" Alert min %i max %i",
00524 edt_adt7461_get_alert_low(edt_p),
00525 edt_adt7461_get_alert_high(edt_p));
00526
00527 printf(" Therm %d Hyster %d",
00528 edt_adt7461_get_therm(edt_p),
00529 edt_adt7461_get_therm_hysteresis(edt_p));
00530
00531 printf(" Stat 0x%02x T Reset %s",
00532 edt_adt7461_reg_read(edt_p, EDT_ADT7461_STATUS_REG_R),
00533 (edt_adt7461_get_therm_reset(edt_p)) ? "On ":"Off"
00534 );
00535
00536
00537
00538 }
00539 if (alert) {
00540 printf(" ALERT");
00541 }
00542 if (therm) {
00543 printf(" THERM");
00544 }
00545
00546 printf("\n");
00547 }
00548