Author: wmb Date: 2010-01-28 03:44:36 +0100 (Thu, 28 Jan 2010) New Revision: 1715
Modified: cpu/x86/pc/olpc/nandcastui.fth dev/usb2/device/net/ax8817x.fth ofw/inet/ip.fth ofw/inet/netload.fth Log: Multicast improvements.
Modified: cpu/x86/pc/olpc/nandcastui.fth =================================================================== --- cpu/x86/pc/olpc/nandcastui.fth 2010-01-27 06:21:04 UTC (rev 1714) +++ cpu/x86/pc/olpc/nandcastui.fth 2010-01-28 02:44:36 UTC (rev 1715) @@ -100,12 +100,18 @@ " boot rom:nb_rx ,,239.255.1.2" eval ;
-: nb-rx +: nb-xx false to already-go? boot-as-call( " boot rom:nb_rx ,,239.255.1.2" eval )boot-as-call ; +: nb-rx + false to already-go? + boot-as-call( + " boot rom:nb_rx ,,0.0.0.1" eval + )boot-as-call +; : ucastnand false to already-go? " boot rom:nb_rx 10.20.0.16,,10.20.0.44" eval
Modified: dev/usb2/device/net/ax8817x.fth =================================================================== --- dev/usb2/device/net/ax8817x.fth 2010-01-27 06:21:04 UTC (rev 1714) +++ dev/usb2/device/net/ax8817x.fth 2010-01-28 02:44:36 UTC (rev 1715) @@ -135,6 +135,12 @@ ax-mii-hw ;
+8 buffer: multicast-filter + +: ax-multi-filter! ( -- ) + multicast-filter 8 0 0 h# 16 ax-control-set +; + : ax-init-mii ( -- ) ax-mii-sw \ ax88772? if @@ -233,7 +239,39 @@ ax-auto-neg-wait ; : ax-promiscuous ( -- ) rx-ctl@ 1 or rx-ctl! ; -: ax-set-multicast ( adr len -- ) 2drop rx-ctl@ 2 or rx-ctl! ; + +: crc32-le ( adr len crc0 -- crc1 ) + -rot bounds ?do ( crc ) + i c@ xor ( crc' ) + 8 0 do ( crc ) + dup 1 and 0<> h# edb88320 and ( crc poly ) + swap u2/ xor ( crc' ) + loop ( crc ) + loop ( crc ) +; + +\ index 000 001 010 011 100 101 110 111 +\ bitrev 000 100 010 110 001 101 011 111 +create bitrev3 0 c, 4 c, 2 c, 6 c, 1 c, 5 c, 3 c, 7 c, + +: add-multicast-address ( adr len -- ) + h# ffffffff crc32-le ( crc ) + \ The low 3 bits - reversed - are the byte index and + \ the next 3 bits - reversed - are the bit number + dup 3 rshift 7 and bitrev3 + c@ ( crc bit# ) + 1 swap lshift ( crc bitmask ) + swap 7 and bitrev3 + c@ ( bitmask byte# ) + multicast-filter + tuck ( adr bitmask adr ) + c@ or swap c! ( ) +; + +\ : ax-set-multicast ( adr len -- ) 2drop rx-ctl@ 2 or rx-ctl! ; +: ax-set-multicast ( adr len -- ) + multicast-filter 8 erase ( adr len ) + add-multicast-address ( ) + ax-multi-filter! ( ) + rx-ctl@ h# 10 or rx-ctl! +; : ax-stop-mac ( -- ) 0 rx-ctl! ;
: ax-init-nic ( -- ) \ Per ax8817x_bind
Modified: ofw/inet/ip.fth =================================================================== --- ofw/inet/ip.fth 2010-01-27 06:21:04 UTC (rev 1714) +++ ofw/inet/ip.fth 2010-01-28 02:44:36 UTC (rev 1715) @@ -84,6 +84,10 @@ swap unknown-ip-addr? or ( flag ) ;
+: multicast-ip-addr? ( adr-buf -- flag ) + c@ h# f0 and h# e0 = +; + : netmask ( -- 'ip ) subnetmask unknown-ip-addr? if default-netmask else subnetmask then ; @@ -185,6 +189,8 @@ drop ip-length xw@ ip-version c@ h# f and /l* payload ;
+0 instance value multicast-rx? + : ip-addr-match? ( -- flag ) \ If we know the server's IP address (e.g. the user specified one, or \ we chose one from a RARP or BOOTP reply, or we locked onto one that @@ -200,6 +206,10 @@ \ If we don't know our own IP address yet, we accept every IP packet my-ip-addr unknown-ip-addr? if true exit then
+ multicast-rx? if + ip-dest-addr multicast-ip-addr? if true exit then + then + \ Otherwise, we know our IP address, so we filter out packets addressed \ to other destinations. my-ip-addr ip-dest-addr ip=
Modified: ofw/inet/netload.fth =================================================================== --- ofw/inet/netload.fth 2010-01-27 06:21:04 UTC (rev 1714) +++ ofw/inet/netload.fth 2010-01-28 02:44:36 UTC (rev 1715) @@ -434,24 +434,45 @@ ." Can't enable multicast reception in network driver" cr ;
+: set-multicast-en-addr ( 'ip -- ) + " "(01 00 5e)" his-en-addr swap move ( 'ip ) + 1+ his-en-addr 3 + 3 move ( ) + his-en-addr 3 + c@ h# 7f and his-en-addr 3 + c! ( ) +; + : send-multicast ( -- ) server-ip-addr his-ip-addr copy-ip-addr - " "(01 00 5e)" his-en-addr swap move ( acf ) - his-ip-addr 1+ his-en-addr 3 + 3 move ( acf ) - his-en-addr 3 + c@ h# 7f and his-en-addr 3 + c! ( ) + his-ip-addr set-multicast-en-addr ;
-: receive-multicast ( -- ) -\ server-ip-addr my-ip-addr copy-ip-addr +0 value igmp-packet +: send-igmp-v1-report ( 'ip -- ) + 8 allocate-ip to igmp-packet ( 'ip ) + 0 igmp-packet l! ( 'ip ) + h# 12 igmp-packet c! ( 'ip ) + dup igmp-packet 4 + copy-ip-addr ( 'ip ) + 0 igmp-packet 8 oc-checksum igmp-packet 2+ be-w! ( 'ip ) + + his-ip-addr copy-ip-addr \ Send to the group we are registering for + 1 ttl ! + igmp-packet 8 2 send-ip-packet + igmp-packet 8 free-ip + broadcast-ip-addr his-ip-addr copy-ip-addr \ Don't filter on the server IP address +; + +: join-multicast-group ( 'ip -- ) + dup set-multicast-en-addr ( 'ip ) + send-igmp-v1-report ( ) + true to multicast-rx? ( ) " set-multicast" my-parent ihandle>phandle find-method if ( acf ) - " "(01 00 5e)" his-en-addr swap move ( acf ) - my-ip-addr 1+ his-en-addr 3 + 3 move ( acf ) - his-en-addr 3 + c@ h# 7f and his-en-addr 3 + c! ( ) his-en-addr /e rot my-parent call-package ( ) exit then try-promiscuous ; +: receive-multicast ( 'ip -- ) + my-ip-addr join-multicast-group +;
defer configured ' noop to configured : configure ( -- )