| | 2764 | # $_[0]: Reference to an opened file handle |
|---|
| | 2765 | # Returns: 1 if the device is safe to access, 0 else. |
|---|
| | 2766 | # This function is meant to prevent access to 1-register-only devices, |
|---|
| | 2767 | # which are designed to be accessed with SMBus receive byte and SMBus send |
|---|
| | 2768 | # byte transactions (i.e. short reads and short writes) and treat SMBus |
|---|
| | 2769 | # read byte as a real write followed by a read. The device detection |
|---|
| | 2770 | # routines would write random values to the chip with possibly very nasty |
|---|
| | 2771 | # results for the hardware. Note that this function won't catch all such |
|---|
| | 2772 | # chips, as it assumes that reads and writes relate to the same register, |
|---|
| | 2773 | # but that's the best we can do. |
|---|
| | 2774 | sub i2c_safety_check |
|---|
| | 2775 | { |
|---|
| | 2776 | my ($file) = @_; |
|---|
| | 2777 | my $data; |
|---|
| | 2778 | |
|---|
| | 2779 | # First we receive a byte from the chip, and remember it. |
|---|
| | 2780 | $data = i2c_smbus_read_byte($file); |
|---|
| | 2781 | return 1 if ($data < 0); |
|---|
| | 2782 | |
|---|
| | 2783 | # We receive a byte again; very likely to be the same for |
|---|
| | 2784 | # 1-register-only devices. |
|---|
| | 2785 | return 1 if (i2c_smbus_read_byte($file) != $data); |
|---|
| | 2786 | |
|---|
| | 2787 | # Then we try a standard byte read, with a register offset equal to |
|---|
| | 2788 | # the byte we received; we should receive the same byte value in return. |
|---|
| | 2789 | return 1 if (i2c_smbus_read_byte_data($file, $data) != $data); |
|---|
| | 2790 | |
|---|
| | 2791 | # Then we try a standard byte read, with a slightly different register |
|---|
| | 2792 | # offset; we should again receive the same byte value in return. |
|---|
| | 2793 | return 1 if (i2c_smbus_read_byte_data($file, $data ^ 1) != ($data ^ 1)); |
|---|
| | 2794 | |
|---|
| | 2795 | # Apprently this is a 1-register-only device, restore the original register |
|---|
| | 2796 | # value and leave it alone. |
|---|
| | 2797 | i2c_smbus_read_byte_data($file, $data); |
|---|
| | 2798 | return 0; |
|---|
| | 2799 | } |
|---|
| | 2800 | |
|---|