summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFelix Fietkau <nbd@openwrt.org>2013-06-09 00:56:35 +0200
committerFelix Fietkau <nbd@openwrt.org>2013-06-09 00:56:35 +0200
commita54ab694cdad2a5b50159a27e2f79df4b4a1e8bd (patch)
treef45895a1fc2d904b9b95a1f467cd396dda6d001b
parented0e0e939dbf9cc53ff13d1c4853cdccbd3c4ba2 (diff)
codegen: work around firmware bug, only accept the first found tlv
-rwxr-xr-xdata/gen-code.pl16
1 files changed, 14 insertions, 2 deletions
diff --git a/data/gen-code.pl b/data/gen-code.pl
index 71b738d..c903d6b 100755
--- a/data/gen-code.pl
+++ b/data/gen-code.pl
@@ -132,9 +132,12 @@ sub gen_tlv_parse_field($$$$) {
}
}
-sub gen_tlv_type($$) {
+sub gen_tlv_type($$$) {
my $cname = shift;
my $elem = shift;
+ my $idx = shift;
+ my $idx_word = "found[".int($idx / 32)."]";
+ my $idx_bit = "(1 << ".($idx % 32).")";
my $type = $elem->{"format"};
my $id = $elem->{"id"};
@@ -146,6 +149,10 @@ sub gen_tlv_type($$) {
print <<EOF;
case $id:
+ if ($idx_word & $idx_bit)
+ break;
+
+ $idx_word |= $idx_bit;
EOF
my $val = $tlv_get{$type};
@@ -188,9 +195,14 @@ sub gen_parse_func($$)
EOF
if (gen_has_types($data)) {
+ my $n_bits = scalar @$data;
+ my $n_words = int(($n_bits + 31) / 32);
+ my $i = 0;
+
print <<EOF;
struct tlv *tlv;
int i;
+ uint32_t found[$n_words] = {};
memset(res, 0, sizeof(*res));
@@ -203,7 +215,7 @@ EOF
EOF
foreach my $field (@$data) {
my $cname = gen_cname($field->{name});
- gen_tlv_type($cname, $field);
+ gen_tlv_type($cname, $field, $i++);
}
print <<EOF;