mac80211.sh 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217
  1. #!/bin/sh
  2. append DRIVERS "mac80211"
  3. check_mac80211_device() {
  4. local device="$1"
  5. local path="$2"
  6. local macaddr="$3"
  7. [ -n "$found" ] && return 0
  8. phy_path=
  9. config_get phy "$device" phy
  10. json_select wlan
  11. [ -n "$phy" ] && case "$phy" in
  12. phy*)
  13. [ -d /sys/class/ieee80211/$phy ] && \
  14. phy_path="$(iwinfo nl80211 path "$dev")"
  15. ;;
  16. *)
  17. if json_is_a "$phy" object; then
  18. json_select "$phy"
  19. json_get_var phy_path path
  20. json_select ..
  21. elif json_is_a "${phy%.*}" object; then
  22. json_select "${phy%.*}"
  23. json_get_var phy_path path
  24. json_select ..
  25. phy_path="$phy_path+${phy##*.}"
  26. fi
  27. ;;
  28. esac
  29. json_select ..
  30. [ -n "$phy_path" ] || config_get phy_path "$device" path
  31. [ -n "$path" -a "$phy_path" = "$path" ] && {
  32. found=1
  33. return 0
  34. }
  35. config_get dev_macaddr "$device" macaddr
  36. [ -n "$macaddr" -a "$dev_macaddr" = "$macaddr" ] && found=1
  37. return 0
  38. }
  39. __get_band_defaults() {
  40. local phy="$1"
  41. ( iw phy "$phy" info; echo ) | awk '
  42. BEGIN {
  43. bands = ""
  44. }
  45. ($1 == "Band" || $1 == "") && band {
  46. if (channel) {
  47. mode="NOHT"
  48. if (ht) mode="HT20"
  49. if (vht && band != "1:") mode="VHT80"
  50. if (he) mode="HE80"
  51. if (he && band == "1:") mode="HE20"
  52. sub("\\[", "", channel)
  53. sub("\\]", "", channel)
  54. bands = bands band channel ":" mode " "
  55. }
  56. band=""
  57. }
  58. $1 == "Band" {
  59. band = $2
  60. channel = ""
  61. vht = ""
  62. ht = ""
  63. he = ""
  64. }
  65. $0 ~ "Capabilities:" {
  66. ht=1
  67. }
  68. $0 ~ "VHT Capabilities" {
  69. vht=1
  70. }
  71. $0 ~ "HE Iftypes" {
  72. he=1
  73. }
  74. $1 == "*" && $3 == "MHz" && $0 !~ /disabled/ && band && !channel {
  75. channel = $4
  76. }
  77. END {
  78. print bands
  79. }'
  80. }
  81. get_band_defaults() {
  82. local phy="$1"
  83. for c in $(__get_band_defaults "$phy"); do
  84. local band="${c%%:*}"
  85. c="${c#*:}"
  86. local chan="${c%%:*}"
  87. c="${c#*:}"
  88. local mode="${c%%:*}"
  89. case "$band" in
  90. 1) band=2g;;
  91. 2) band=5g;;
  92. 3) band=60g;;
  93. 4) band=6g;;
  94. *) band="";;
  95. esac
  96. [ -n "$band" ] || continue
  97. [ -n "$mode_band" -a "$band" = "6g" ] && return
  98. mode_band="$band"
  99. channel="$chan"
  100. htmode="$mode"
  101. done
  102. }
  103. check_devidx() {
  104. case "$1" in
  105. radio[0-9]*)
  106. local idx="${1#radio}"
  107. [ "$devidx" -ge "${1#radio}" ] && devidx=$((idx + 1))
  108. ;;
  109. esac
  110. }
  111. check_board_phy() {
  112. local name="$2"
  113. json_select "$name"
  114. json_get_var phy_path path
  115. json_select ..
  116. if [ "$path" = "$phy_path" ]; then
  117. board_dev="$name"
  118. elif [ "${path%+*}" = "$phy_path" ]; then
  119. fallback_board_dev="$name.${path#*+}"
  120. fi
  121. }
  122. detect_mac80211() {
  123. devidx=0
  124. config_load wireless
  125. config_foreach check_devidx wifi-device
  126. json_load_file /etc/board.json
  127. for _dev in /sys/class/ieee80211/*; do
  128. [ -e "$_dev" ] || continue
  129. dev="${_dev##*/}"
  130. mode_band=""
  131. channel=""
  132. htmode=""
  133. ht_capab=""
  134. get_band_defaults "$dev"
  135. path="$(iwinfo nl80211 path "$dev")"
  136. macaddr="$(cat /sys/class/ieee80211/${dev}/macaddress)"
  137. # work around phy rename related race condition
  138. [ -n "$path" -o -n "$macaddr" ] || continue
  139. board_dev=
  140. fallback_board_dev=
  141. json_for_each_item check_board_phy wlan
  142. [ -n "$board_dev" ] || board_dev="$fallback_board_dev"
  143. [ -n "$board_dev" ] && dev="$board_dev"
  144. found=
  145. config_foreach check_mac80211_device wifi-device "$path" "$macaddr"
  146. [ -n "$found" ] && continue
  147. name="radio${devidx}"
  148. devidx=$(($devidx + 1))
  149. case "$dev" in
  150. phy*)
  151. if [ -n "$path" ]; then
  152. dev_id="set wireless.${name}.path='$path'"
  153. else
  154. dev_id="set wireless.${name}.macaddr='$macaddr'"
  155. fi
  156. ;;
  157. *)
  158. dev_id="set wireless.${name}.phy='$dev'"
  159. ;;
  160. esac
  161. uci -q batch <<-EOF
  162. set wireless.${name}=wifi-device
  163. set wireless.${name}.type=mac80211
  164. ${dev_id}
  165. set wireless.${name}.channel=${channel}
  166. set wireless.${name}.band=${mode_band}
  167. set wireless.${name}.htmode=$htmode
  168. set wireless.${name}.disabled=1
  169. set wireless.default_${name}=wifi-iface
  170. set wireless.default_${name}.device=${name}
  171. set wireless.default_${name}.network=lan
  172. set wireless.default_${name}.mode=ap
  173. set wireless.default_${name}.ssid=OpenWrt
  174. set wireless.default_${name}.encryption=none
  175. EOF
  176. uci -q commit wireless
  177. done
  178. }