blob: ede1eadc56274cfdb938487bad1e9b6f3885726d [file] [log] [blame]
\ See license at end of file
purpose: Driver for the MMP3 thermal sensor
0 0 " d403b000" " /" begin-package
" thermal" name
" marvell,mmp3-thermal" +compatible
my-address my-space h# 1000 reg
d# 11 encode-int " interrupts" property
" /interrupt-controller@188" encode-phandle " interrupt-parent" property
0 " #thermal-sensor-cells" integer-property
" /clocks" encode-phandle
mmp2-thermal0-clk# encode-int encode+
" /clocks" encode-phandle encode+
mmp3-thermal1-clk# encode-int encode+
" /clocks" encode-phandle encode+
mmp3-thermal2-clk# encode-int encode+
" /clocks" encode-phandle encode+
mmp3-thermal3-clk# encode-int encode+ " clocks" property
" THSENS1" encode-string
" THSENS2" encode-string encode+
" THSENS3" encode-string encode+
" THSENS4" encode-string encode+ " clock-names" property
end-package
dev /
new-device
" thermal-zones" device-name
new-device
" cpu-thermal" device-name
d# 1000 " polling-delay" integer-property
0 " polling-delay-passive" integer-property
" /thermal" encode-phandle " thermal-sensors" property
new-device
" trips" device-name
new-device
" cpu-crit" device-name
d# 100500 " temperature" integer-property
0 " hysteresis" integer-property
" critical" " type" string-property
finish-device
new-device
" cpu-hot" device-name
d# 85000 " temperature" integer-property
0 " hysteresis" integer-property
" hot" " type" string-property
finish-device
finish-device
new-device
" cooling-maps" device-name
finish-device
finish-device
finish-device
device-end
\ FIXME: characterise the observations using an IR thermometer,
\ because the datasheet and the registers manual disagree on
\ interpretation of these gray code values.
create gc0 \ high range
d# 780 w, \ 0000
d# 805 w, \ 0001
d# 855 w, \ 0010
d# 830 w, \ 0011
d# 955 w, \ 0100
d# 930 w, \ 0101
d# 880 w, \ 0110
d# 905 w, \ 0111
d# 0 w, \ 1000
d# 1130 w, \ 1001
d# 1080 w, \ 1010
d# 1105 w, \ 1011
d# 980 w, \ 1100
d# 1005 w, \ 1101
d# 1055 w, \ 1110
d# 1030 w, \ 1111
create gc1 \ low range
d# 260 w, \ 0000
d# 285 w, \ 0001
d# 335 w, \ 0010
d# 310 w, \ 0011
d# 435 w, \ 0100
d# 410 w, \ 0101
d# 360 w, \ 0110
d# 385 w, \ 0111
d# 0 w, \ 1000
d# 610 w, \ 1001
d# 560 w, \ 1010
d# 585 w, \ 1011
d# 460 w, \ 1100
d# 485 w, \ 1101
d# 535 w, \ 1110
d# 510 w, \ 1111
: gc>c ( gray-code -- tenths-of-celcius )
dup h# 0800.0000 and ( gray-code low-range? )
if gc1 else gc0 then ( gray-code table )
swap h# f and wa+ w@
;
: ts-clock ( offset -- )
7 over apbc! 3 swap apbc! ( n )
;
: ts-clocks
h# 90 ts-clock
h# 98 ts-clock
h# 9c ts-clock
h# a0 ts-clock
;
h# 03.b000 value tsense \ p2021
: +ts ( offset -- io-offset ) tsense swap la+ ;
: ts@ ( offset -- l ) +ts io@ ;
: ts! ( l offset -- ) +ts io! ;
\ last system reset was caused by thermal sensor?
\ : tsr? ( -- flag ) h# 0028 mpmu@ h# 10 and ; \ p282
\ : tsr? ( -- flag ) h# 1028 mpmu@ h# 10 and ; \ p311
\ last thermal sensor watchdog reset was caused by THSENS1 unit?
\ (polarity differs from documentation)
\ : thsens1? ( -- flag ) h# 00a4 mpmu@ h# 10 and ; \ p345
\ thsens1 is requesting interrupt service? (true if auto run enabled)
\ : thsens1-int? ( -- flag ) h# 00a4 mpmu@ h# 1 and ; \ p346
\ thermal sensor interrupt is masked? (normally true)
\ : thsens1-int-masked? h# 180 icu@ 800 and ; \ p700
\ : thsens1-int-status? h# 188 icu@ 800 and ; \ p702
\ thermal sensor watchdog to system reset enable (normally already set)
\ : wdtr? h# 200 mpmu@ 1 7 lshift and 0= ; \ p302
: ts-auto-read ( n -- ) \ undocumented
dup ts@ h# 20.0000 or swap ts!
;
: ts-wait ( n -- )
d# 10 get-msecs + ( n limit )
begin
over ts@ h# 2000.0000 and ( n limit ready? )
if 2drop exit then
dup get-msecs - 0< ( n limit timeout? )
until ( n limit )
2drop ( )
;
: ts-read ( n -- gc )
dup ts-wait ( n )
ts@ ( gc )
;
: ts-range-low ( n -- )
dup ts@ h# 0800.0000 or swap ts!
;
: ts-range-high ( n -- )
dup ts@ h# 0800.0000 invert and swap ts!
;
h# 0400.0d00 value ts-watchdog-mask \ 100.5C
: ts-watchdog-on ( n -- )
dup ts@ ts-watchdog-mask or swap ts!
;
: ts-watchdog-off ( n -- )
dup ts@ ts-watchdog-mask invert and swap ts!
;
: init-thermal-sensor ( -- )
ts-clocks
0 ts-range-high
0 ts-watchdog-on
\ WDT reset causes SoC hang, per errata 472630, on XO-4 A2 and B1,
\ but is detected and handled by EC
1 ts-range-low
2 ts-range-low
3 0 do i ts-auto-read loop
;
\ for testing, swing our normally highrange sensor back to lowrange
: 0ts-low
0 ts-watchdog-off
0 ts-range-low
;
\ read and average the two sensors on lowrange duty
: cpu-temperature ( -- celcius )
1 ts-read gc>c
2 ts-read gc>c
+ d# 20 /
;
: ?thermal ( -- )
0 ts-read gc>c d# 850 > abort " CPU too hot"
;
: .c.c ( n -- ) 0 <# # [char] . hold #s #> type ." C " ;
: .c ( n -- ) (.) type ." C " ;
: .thermal
push-decimal
time&date >unix-seconds .
." sensors: "
0 ts@ dup h# f and 0= if drop ." <80C " else gc>c .c.c then
1 ts@ gc>c .c.c \ FIXME: show <n and >n too here
2 ts@ gc>c .c.c
." cpu: " cpu-temperature .c
[ifdef] .bat-temp
." battery: " .bat-temp ." C "
[then]
pop-base
;
: watch-thermal
begin
.thermal cr d# 1000 ms key?
until key drop cr
;
\ .thermal 0 ts@ f and . d# 1000 ms cr many
string-array tsense-regx-bits
," 31=reserved"
," 30=start"
," 29=status"
," 28=over_int"
," 27=lowrange"
," 26=en_wdog"
," 25=temp_int"
," 24=en_over_int"
," 23=en_temp_int"
," 22=reserved"
," 21=auto_read_en"
end-string-array
: .tc ( n n -- )
.
push-decimal
gc>c .c.c
pop-base
;
: .tsense ( n -- )
dup . cr 4 spaces
d# 11 0 do
dup i lshift h# 8000.0000 and if
i tsense-regx-bits count type space
then
loop cr
4 spaces dup dup 8 rshift h# f and ." wdog_tshld=" .tc cr
4 spaces dup dup 4 rshift h# f and ." int_tshld=" .tc cr
4 spaces dup dup h# f and ." temp_value=" .tc cr
drop
;
: .ts
0 ts@ ." tsense_reg[0]=" .tsense
1 ts@ ." tsense_reg[1]=" .tsense
2 ts@ ." tsense_reg[2]=" .tsense
;
: test-thermal
." press against heat spreader and press a key once temperature is low"
watch-thermal
h# 200 mpmu@ 1 7 lshift and 0= if
." THRSENS_WDTR_EN was not set" cr
h# 200 mpmu@ 1 7 lshift or h# 200 mpmu!
then
1 ts@
1 d# 27 lshift or \ set the lowrange bit
h# 0020.0000 or \ set the autorun bit (undocumented)
h# 0400.0000 or \ set the watchdog enable bit
h# b h# f and d# 8 lshift or \ set the watchdog temperature (58-60.5C)
b# 0101.1111.1010.0000.0000.1111.1111.0000
and \ always write zero to reserved bits
1 ts!
." thermal watchdog enabled" cr
watch-thermal
;
: force-thermal-watchdog
h# 200 mpmu@ 1 7 lshift or h# 200 mpmu! \ thrsens_wdtr_en
h# 0c20.0000 h# 03.b004 io! \ lowrange, en_wdog, auto_read_en, wdog_tshld 26C
;
stand-init: Thermal sensor
init-thermal-sensor
;
\ LICENSE_BEGIN
\ Copyright (c) 2012 FirmWorks
\
\ Permission is hereby granted, free of charge, to any person obtaining
\ a copy of this software and associated documentation files (the
\ "Software"), to deal in the Software without restriction, including
\ without limitation the rights to use, copy, modify, merge, publish,
\ distribute, sublicense, and/or sell copies of the Software, and to
\ permit persons to whom the Software is furnished to do so, subject to
\ the following conditions:
\
\ The above copyright notice and this permission notice shall be
\ included in all copies or substantial portions of the Software.
\
\ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
\ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
\ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
\ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
\ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
\ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
\ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
\
\ LICENSE_END