[openfirmware] [commit] r2198 - cpu/x86/pc/olpc
repository service
svn at openfirmware.info
Fri May 13 00:09:18 CEST 2011
Author: wmb
Date: Fri May 13 00:09:17 2011
New Revision: 2198
URL: http://tracker.coreboot.org/trac/openfirmware/changeset/2198
Log:
OLPC RTC anti-rollback - working version.
Modified:
cpu/x86/pc/olpc/guardrtc.fth
cpu/x86/pc/olpc/security.fth
Modified: cpu/x86/pc/olpc/guardrtc.fth
==============================================================================
--- cpu/x86/pc/olpc/guardrtc.fth Tue May 10 19:56:01 2011 (r2197)
+++ cpu/x86/pc/olpc/guardrtc.fth Fri May 13 00:09:17 2011 (r2198)
@@ -70,6 +70,7 @@
flash-open ( )
(put-mfg-data) ( )
flash-close ( )
+ d# 1000 ms ( ) \ Give the EC time to restart
;
: flash-write-some ( adr len offset -- )
flash-open ( adr len offset )
@@ -142,31 +143,41 @@
update-timestamp ( status )
;
-1 buffer: byte-buf
-: encode-byte ( b -- ) byte-buf c! byte-buf 1 encode-bytes ;
: +encode-bytes ( prop$ $ -- prop$' ) encode-bytes encode+ ;
-: make-timestamp-property ( -- )
- rtc-timestamp 0= if exit then
- " /chosen" find-package drop push-package ( )
- rtc-timestamp unix-seconds> ( s m h d m y )
- push-decimal ( s m h d m y )
- #timestamps (.) encode-bytes ( s m h d m y prop$ )
- " ," +encode-bytes rot (.4) +encode-bytes ( s m h d m prop$ )
- " -" +encode-bytes rot (.2) +encode-bytes ( s m h d prop$' )
- " -" +encode-bytes rot (.2) +encode-bytes ( s m h prop$' )
- " @" +encode-bytes rot (.2) +encode-bytes ( s m prop$' )
- " :" +encode-bytes rot (.2) +encode-bytes ( s prop$' )
- " :" +encode-bytes rot (.2) +encode-bytes ( prop$' )
- " "(00)" +encode-bytes ( prop$' )
- pop-base ( )
-
- " rtc-timestamp" (property) ( )
- pop-package
-;
-: make-status-property ( value$ -- )
- " /chosen" find-package drop push-package ( value$ )
+string-array rtc-status-names
+ ," ok"
+ ," empty"
+ ," residue"
+ ," rollback"
+end-string-array
+
+: make-rtc-properties ( status -- )
+ " /chosen" find-package drop push-package ( status )
+
+ rtc-status-names count
encode-string " rtc-status" (property) ( )
+
+ rtc-timestamp if
+ rtc-timestamp unix-seconds> ( s m h d m y )
+ push-decimal ( s m h d m y )
+ (.4) encode-bytes ( s m h d m prop$ )
+ rot (.2) +encode-bytes ( s m h d prop$' )
+ rot (.2) +encode-bytes ( s m h prop$' )
+ " T" +encode-bytes ( s m h prop$' )
+ rot (.2) +encode-bytes ( s m prop$' )
+ rot (.2) +encode-bytes ( s prop$' )
+ rot (.2) +encode-bytes ( prop$' )
+ " Z"(00)" +encode-bytes ( prop$' )
+ pop-base ( )
+
+ " rtc-timestamp" (property) ( )
+ then
+
+ push-decimal
+ #timestamps (.) encode-bytes " rtc-count" (property) ( )
+ pop-base
+
pop-package
;
@@ -178,24 +189,19 @@
then ( flag )
;
-: rtc-rollback? ( -- flag )
+: rtc-rollback? ( -- error? )
rtcar-enabled? 0= if exit then
find-timestamp ( status )
?update-timestamp ( status' )
- make-timestamp-property ( status )
- case
- 0 of " ok" make-status-property false endof
- 1 of " empty" make-status-property false endof
- 2 of " residue" make-status-property true endof
- 3 of " rollback" make-status-property true endof
- ( default ) true swap
- endcase
+ dup make-rtc-properties ( status )
+ 2 >= ( error? )
;
-: parse-field ( val$ delimiter expected-length -- val$' field$ )
- >r left-parse-string ( val$' field$ )
- dup r> <> throw
+: parse-field ( val$ length -- val$' field$ )
+ 2dup < throw ( val$ length )
+ >r over r@ ( val$ adr length r: length )
+ 2swap r> /string 2swap ( val$' field$ )
;
\ Throws an error if either a number is unparsable or out of range
: decode-number ( field$ min max -- n )
@@ -206,48 +212,47 @@
;
: decode-timestamp ( val$ -- s m h d m y )
- [char] - 4 parse-field d# 2000 d# 2099 decode-number >r ( val$' r: y )
- [char] - 2 parse-field 1 d# 12 decode-number >r ( val$' r: y m )
- [char] @ 2 parse-field 1 d# 31 decode-number >r ( val$' r: y m d )
- [char] : 2 parse-field 0 d# 23 decode-number >r ( val$' r: y m d h )
- [char] : 2 parse-field 0 d# 59 decode-number >r ( val$' r: y m d h m )
- dup 2 <> throw 0 d# 59 decode-number >r ( r: y m d h m s )
- r> r> r> r> r> r> ( s m h d m y )
-;
-: fix-rtc-timestamps ( data$ -- ) \ "count old-ts new-ts" e.g. 2011-10-12,00:23:45
- bl left-parse-string ( rem$ count$ )
-
- 0 h# 7fffffff ['] decode-number catch if ( rem$ x x x x )
- 4drop 2drop ." Bad count format" cr ( )
- exit ( -- )
- then ( rem$ count )
- -rot ( count rem$ )
-
- find-timestamp ( count rem$ )
-
- bl left-parse-string ( count rem$ old-timestamp$ )
- 2dup " no-timestamp" $= if ( count rem$ old-timestamp$ )
- 2drop ( count rem$ )
- rtc-timestamp if ( count rem$ )
- 3drop ( )
+ 4 parse-field d# 2000 d# 2099 decode-number >r ( val$' r: y )
+ 2 parse-field 1 d# 12 decode-number >r ( val$' r: y m )
+ 2 parse-field 1 d# 31 decode-number >r ( val$' r: y m d )
+ 1 parse-field drop c@ [char] T <> throw ( val$' r: y m d )
+ 2 parse-field 0 d# 23 decode-number >r ( val$' r: y m d h )
+ 2 parse-field 0 d# 59 decode-number >r ( val$' r: y m d h m )
+ 2 parse-field 0 d# 59 decode-number >r ( val$' r: y m d h m s )
+ 1 parse-field drop c@ [char] Z <> throw ( val$' r: y m d h m s )
+ nip 0<> throw ( r: y m d h m s )
+ r> r> r> r> r> r> ( s m h d m y )
+;
+: fix-rtc-timestamps ( newrtc$ nonce$ -- currentrtc$ )
+ find-timestamp drop ( newrtc$ nonce$ currentrtc$ )
+
+ 2dup " 00000000T000000Z" $= if ( newrtc$ nonce$ currentrtc$ )
+ 2drop ( newrtc$ nonce$ )
+ rtc-timestamp if ( newrtc$ nonce$ )
+ 4drop ( )
." Old timestamp mismatch" cr ( )
exit ( -- )
- then
- else ( count rem$ old-timestamp$ )
- ['] decode-timestamp catch if ( count rem$ x x )
- 5drop ( )
+ then ( newrtc$ nonce$ )
+ else ( newrtc$ nonce$ currentrtc$ )
+ ['] decode-timestamp catch if ( newrtc$ nonce$ x x )
+ 2drop 4drop ( )
." Bad timestamp format" cr ( )
exit ( -- )
- then ( count rem$ s m h d m y )
- then ( count rem$ s m h d m y )
+ then ( newrtc$ nonce$ s m h d m y )
+ >unix-seconds ( newrtc$ nonce$ timestamp )
+ rtc-timestamp <> if ( newrtc$ nonce$ )
+ 4drop ( )
+ ." Old timestamp mismatch" cr ( )
+ exit ( -- )
+ then ( newrtc$ nonce$ )
+ then ( newrtc$ nonce$ )
- >unix-seconds ( count rem$ old-timestamp )
- rtc-timestamp <> if ( count rem$ )
- 3drop ( )
- ." Old timestamp mismatch" cr ( )
+ 0 h# 7fffffff ['] decode-number catch if ( newrtc$ x x x x )
+ 4drop 2drop ." Bad count format" cr ( )
exit ( -- )
- then ( count rem$ )
- rot init-timestamp-area ( rem$ )
+ then ( newrtc$ count )
+
+ init-timestamp-area ( newrtc$ )
['] decode-timestamp catch if ( x x )
2drop ." Bad timestamp format" cr ( )
Modified: cpu/x86/pc/olpc/security.fth
==============================================================================
--- cpu/x86/pc/olpc/security.fth Tue May 10 19:56:01 2011 (r2197)
+++ cpu/x86/pc/olpc/security.fth Fri May 13 00:09:17 2011 (r2198)
@@ -955,37 +955,102 @@
r> to debug-security?
;
-: fix-rtc-history ( data$ -- ) \ SN UUID counter timestamp newtimestamp
- \ Isolate data from first line
+
+0 [if]
+\ SN : UUID : currrtc : nonce : newrtc
+\ 0 11 12 48 49 65 66 76 77 (93)
+d# 11 1+ d# 36 + 1+ d# 16 + 1+ d# 10 + 1+ d# 16 +
+constant /rtc-signature
+/rtc-signature buffer: rtc-signature-buf
+
+: check-rtc-signature ( sig$ currentrtc$ nonce$ newrtc$ -- good? )
+
+ rtc-signature-buf d# 77 + swap move ( sig$ currentrtc$ nonce$ )
+ [char] : rtc-signature-buf d# 76 + c! ( sig$ currentrtc$ nonce$ )
+
+ rtc-signature-buf d# 66 + swap move ( sig$ currentrtc$ )
+ [char] : rtc-signature-buf d# 65 + c! ( sig$ currentrtc$ )
+
+ rtc-signature-buf d# 49 + swap move ( sig$ )
+
+ \ Copy SN:UUID: from machine-id-buf to rtc-signature-buf
+ machine-id-buf d# 49 rtc-signature-buf move ( sig$ )
+
+ rtc-signature-buf /rtc-signature 2swap ( data$ sig$ )
+ " sha256" signature-good? ( good? )
+;
+ newrtc$ rtc-signature-buf d# 77 + swap move ( )
+ [char] : rtc-signature-buf d# 76 + c! ( )
+
+ nonce$ rtc-signature-buf d# 66 + swap move ( )
+ [char] : rtc-signature-buf d# 65 + c! ( )
+
+ currentrtc$ rtc-signature-buf d# 49 + swap move ( )
+ [char] : rtc-signature-buf d# 48 + c! ( )
+
+[then]
+
+0 0 2value currentrtc$
+0 0 2value newrtc$
+0 0 2value nonce$
+0 0 2value rtcsig$
+: rtc-format-error ( -- done? )
+ ." RTC Reset format error" ?lease-error-cr true
+;
+: check-rtc-key ( data$ -- done? ) \ rtc01: SN currentrtc nonce newrtc sig0N: ...
+ \ Isolate data from line
newline left-parse-string 2nip ( rem$ )
+ bl left-parse-string " rtc01:" $= 0= if ( rem$ )
+ ." Unknown format" ?lease-error-cr ( rem$ )
+ 2drop true exit ( -- true )
+ then ( rem$ )
+
bl left-parse-string ( rem$ serial$ )
my-sn$ $= 0= if ( rem$ )
- ." Wrong serial number" ?lease-error-cr ( rem$ )
- 2drop exit ( -- )
+\ ." Wrong serial number" ?lease-error-cr ( rem$ )
+ 2drop false exit ( -- false )
then ( rem$ )
- \ Ignore UUID for now
- bl left-parse-string ( rem$ uuid$ )
- 2drop ( rem$ )
-
- fix-rtc-timestamps ( )
+ bl left-parse-string to currentrtc$ ( rem$' )
+ bl left-parse-string to nonce$ ( rem$' )
+ bl left-parse-string to newrtc$ ( rem$' )
+ to rtcsig$ ( )
+
+ currentrtc$ nip d# 16 <> if rtc-format-error exit then
+ nonce$ nip d# 10 <> if rtc-format-error exit then
+ newrtc$ nip d# 16 <> if rtc-format-error exit then
+
+ newrtc$ nonce$ currentrtc$ machine-id-buf d# 48 " %s:%s:%s:%s" sprintf ( data$ )
+
+ rtcsig$ " sha256" signature-good? if ( )
+ newrtc$ nonce$ currentrtc$ fix-rtc-timestamps ( )
+ else
+ ." Bad signature " ?lease-error-cr ( )
+ then ( )
+ true ( done? )
;
: ?rtc-update ( -- )
rtcar-enabled? 0= if exit then
show-dot
null$ cn-buf place
- " rtcreset" bundle-present? if
+ " rtcreset.sig" open-security? if exit then >r ( r: ih )
" RTCRESET found - " ?lease-debug
+ load-started
leasekey$ to pubkey$
- img$ sig$ sha-valid? if
- img$ fix-rtc-history
- show-unlock
- else
- show-lock
- then
- then
+ begin
+ sec-line-buf /sec-line-max r@ read-line if ( actual -eof? )
+ 2drop r> close-file drop exit
+ then ( actual -eof? )
+ while ( actual )
+ sec-line-buf swap check-rtc-key if ( )
+ r> close-file drop exit ( -- )
+ then ( )
+ repeat ( actual )
+ drop ( )
+ " No matching records" ?lease-error-cr ( )
+ r> close-file drop false ( false )
;
: load-from-device ( devname$ -- done? )
More information about the openfirmware
mailing list