@@ -42,18 +42,22 @@ struct btf {
42
42
43
43
struct btf_ext_info {
44
44
/*
45
- * info points to a deep copy of the individual info section
46
- * (e.g. func_info and line_info) from the .BTF.ext.
47
- * It does not include the __u32 rec_size.
45
+ * info points to the individual info section (e.g. func_info and
46
+ * line_info) from the .BTF.ext. It does not include the __u32 rec_size.
48
47
*/
49
48
void * info ;
50
49
__u32 rec_size ;
51
50
__u32 len ;
52
51
};
53
52
54
53
struct btf_ext {
54
+ union {
55
+ struct btf_ext_header * hdr ;
56
+ void * data ;
57
+ };
55
58
struct btf_ext_info func_info ;
56
59
struct btf_ext_info line_info ;
60
+ __u32 data_size ;
57
61
};
58
62
59
63
struct btf_ext_info_sec {
@@ -367,8 +371,6 @@ void btf__free(struct btf *btf)
367
371
368
372
struct btf * btf__new (__u8 * data , __u32 size )
369
373
{
370
- __u32 log_buf_size = 0 ;
371
- char * log_buf = NULL ;
372
374
struct btf * btf ;
373
375
int err ;
374
376
@@ -378,15 +380,6 @@ struct btf *btf__new(__u8 *data, __u32 size)
378
380
379
381
btf -> fd = -1 ;
380
382
381
- log_buf = malloc (BPF_LOG_BUF_SIZE );
382
- if (!log_buf ) {
383
- err = - ENOMEM ;
384
- goto done ;
385
- }
386
-
387
- * log_buf = 0 ;
388
- log_buf_size = BPF_LOG_BUF_SIZE ;
389
-
390
383
btf -> data = malloc (size );
391
384
if (!btf -> data ) {
392
385
err = - ENOMEM ;
@@ -396,17 +389,6 @@ struct btf *btf__new(__u8 *data, __u32 size)
396
389
memcpy (btf -> data , data , size );
397
390
btf -> data_size = size ;
398
391
399
- btf -> fd = bpf_load_btf (btf -> data , btf -> data_size ,
400
- log_buf , log_buf_size , false);
401
-
402
- if (btf -> fd == -1 ) {
403
- err = - errno ;
404
- pr_warning ("Error loading BTF: %s(%d)\n" , strerror (errno ), errno );
405
- if (log_buf && * log_buf )
406
- pr_warning ("%s\n" , log_buf );
407
- goto done ;
408
- }
409
-
410
392
err = btf_parse_hdr (btf );
411
393
if (err )
412
394
goto done ;
@@ -418,8 +400,6 @@ struct btf *btf__new(__u8 *data, __u32 size)
418
400
err = btf_parse_type_sec (btf );
419
401
420
402
done :
421
- free (log_buf );
422
-
423
403
if (err ) {
424
404
btf__free (btf );
425
405
return ERR_PTR (err );
@@ -428,16 +408,45 @@ struct btf *btf__new(__u8 *data, __u32 size)
428
408
return btf ;
429
409
}
430
410
411
+ int btf__load (struct btf * btf )
412
+ {
413
+ __u32 log_buf_size = BPF_LOG_BUF_SIZE ;
414
+ char * log_buf = NULL ;
415
+ int err = 0 ;
416
+
417
+ if (btf -> fd >= 0 )
418
+ return - EEXIST ;
419
+
420
+ log_buf = malloc (log_buf_size );
421
+ if (!log_buf )
422
+ return - ENOMEM ;
423
+
424
+ * log_buf = 0 ;
425
+
426
+ btf -> fd = bpf_load_btf (btf -> data , btf -> data_size ,
427
+ log_buf , log_buf_size , false);
428
+ if (btf -> fd < 0 ) {
429
+ err = - errno ;
430
+ pr_warning ("Error loading BTF: %s(%d)\n" , strerror (errno ), errno );
431
+ if (* log_buf )
432
+ pr_warning ("%s\n" , log_buf );
433
+ goto done ;
434
+ }
435
+
436
+ done :
437
+ free (log_buf );
438
+ return err ;
439
+ }
440
+
431
441
int btf__fd (const struct btf * btf )
432
442
{
433
443
return btf -> fd ;
434
444
}
435
445
436
- void btf__get_strings (const struct btf * btf , const char * * strings ,
437
- __u32 * str_len )
446
+ const void * btf__get_raw_data (const struct btf * btf , __u32 * size )
438
447
{
439
- * strings = btf -> strings ;
440
- * str_len = btf -> hdr -> str_len ;
448
+ * size = btf -> data_size ;
449
+ return btf -> data ;
441
450
}
442
451
443
452
const char * btf__name_by_offset (const struct btf * btf , __u32 offset )
@@ -584,45 +593,38 @@ int btf__get_map_kv_tids(const struct btf *btf, const char *map_name,
584
593
return 0 ;
585
594
}
586
595
587
- struct btf_ext_sec_copy_param {
596
+ struct btf_ext_sec_setup_param {
588
597
__u32 off ;
589
598
__u32 len ;
590
599
__u32 min_rec_size ;
591
600
struct btf_ext_info * ext_info ;
592
601
const char * desc ;
593
602
};
594
603
595
- static int btf_ext_copy_info (struct btf_ext * btf_ext ,
596
- __u8 * data , __u32 data_size ,
597
- struct btf_ext_sec_copy_param * ext_sec )
604
+ static int btf_ext_setup_info (struct btf_ext * btf_ext ,
605
+ struct btf_ext_sec_setup_param * ext_sec )
598
606
{
599
- const struct btf_ext_header * hdr = (struct btf_ext_header * )data ;
600
607
const struct btf_ext_info_sec * sinfo ;
601
608
struct btf_ext_info * ext_info ;
602
609
__u32 info_left , record_size ;
603
610
/* The start of the info sec (including the __u32 record_size). */
604
- const void * info ;
605
-
606
- /* data and data_size do not include btf_ext_header from now on */
607
- data = data + hdr -> hdr_len ;
608
- data_size -= hdr -> hdr_len ;
611
+ void * info ;
609
612
610
613
if (ext_sec -> off & 0x03 ) {
611
614
pr_debug (".BTF.ext %s section is not aligned to 4 bytes\n" ,
612
615
ext_sec -> desc );
613
616
return - EINVAL ;
614
617
}
615
618
616
- if (data_size < ext_sec -> off ||
617
- ext_sec -> len > data_size - ext_sec -> off ) {
619
+ info = btf_ext -> data + btf_ext -> hdr -> hdr_len + ext_sec -> off ;
620
+ info_left = ext_sec -> len ;
621
+
622
+ if (btf_ext -> data + btf_ext -> data_size < info + ext_sec -> len ) {
618
623
pr_debug ("%s section (off:%u len:%u) is beyond the end of the ELF section .BTF.ext\n" ,
619
- ext_sec -> desc , ext_sec -> off , ext_sec -> len );
624
+ ext_sec -> desc , ext_sec -> off , ext_sec -> len );
620
625
return - EINVAL ;
621
626
}
622
627
623
- info = data + ext_sec -> off ;
624
- info_left = ext_sec -> len ;
625
-
626
628
/* At least a record size */
627
629
if (info_left < sizeof (__u32 )) {
628
630
pr_debug (".BTF.ext %s record size not found\n" , ext_sec -> desc );
@@ -634,7 +636,7 @@ static int btf_ext_copy_info(struct btf_ext *btf_ext,
634
636
if (record_size < ext_sec -> min_rec_size ||
635
637
record_size & 0x03 ) {
636
638
pr_debug ("%s section in .BTF.ext has invalid record size %u\n" ,
637
- ext_sec -> desc , record_size );
639
+ ext_sec -> desc , record_size );
638
640
return - EINVAL ;
639
641
}
640
642
@@ -680,42 +682,35 @@ static int btf_ext_copy_info(struct btf_ext *btf_ext,
680
682
ext_info = ext_sec -> ext_info ;
681
683
ext_info -> len = ext_sec -> len - sizeof (__u32 );
682
684
ext_info -> rec_size = record_size ;
683
- ext_info -> info = malloc (ext_info -> len );
684
- if (!ext_info -> info )
685
- return - ENOMEM ;
686
- memcpy (ext_info -> info , info + sizeof (__u32 ), ext_info -> len );
685
+ ext_info -> info = info + sizeof (__u32 );
687
686
688
687
return 0 ;
689
688
}
690
689
691
- static int btf_ext_copy_func_info (struct btf_ext * btf_ext ,
692
- __u8 * data , __u32 data_size )
690
+ static int btf_ext_setup_func_info (struct btf_ext * btf_ext )
693
691
{
694
- const struct btf_ext_header * hdr = (struct btf_ext_header * )data ;
695
- struct btf_ext_sec_copy_param param = {
696
- .off = hdr -> func_info_off ,
697
- .len = hdr -> func_info_len ,
692
+ struct btf_ext_sec_setup_param param = {
693
+ .off = btf_ext -> hdr -> func_info_off ,
694
+ .len = btf_ext -> hdr -> func_info_len ,
698
695
.min_rec_size = sizeof (struct bpf_func_info_min ),
699
696
.ext_info = & btf_ext -> func_info ,
700
697
.desc = "func_info"
701
698
};
702
699
703
- return btf_ext_copy_info (btf_ext , data , data_size , & param );
700
+ return btf_ext_setup_info (btf_ext , & param );
704
701
}
705
702
706
- static int btf_ext_copy_line_info (struct btf_ext * btf_ext ,
707
- __u8 * data , __u32 data_size )
703
+ static int btf_ext_setup_line_info (struct btf_ext * btf_ext )
708
704
{
709
- const struct btf_ext_header * hdr = (struct btf_ext_header * )data ;
710
- struct btf_ext_sec_copy_param param = {
711
- .off = hdr -> line_info_off ,
712
- .len = hdr -> line_info_len ,
705
+ struct btf_ext_sec_setup_param param = {
706
+ .off = btf_ext -> hdr -> line_info_off ,
707
+ .len = btf_ext -> hdr -> line_info_len ,
713
708
.min_rec_size = sizeof (struct bpf_line_info_min ),
714
709
.ext_info = & btf_ext -> line_info ,
715
710
.desc = "line_info" ,
716
711
};
717
712
718
- return btf_ext_copy_info (btf_ext , data , data_size , & param );
713
+ return btf_ext_setup_info (btf_ext , & param );
719
714
}
720
715
721
716
static int btf_ext_parse_hdr (__u8 * data , __u32 data_size )
@@ -755,9 +750,7 @@ void btf_ext__free(struct btf_ext *btf_ext)
755
750
{
756
751
if (!btf_ext )
757
752
return ;
758
-
759
- free (btf_ext -> func_info .info );
760
- free (btf_ext -> line_info .info );
753
+ free (btf_ext -> data );
761
754
free (btf_ext );
762
755
}
763
756
@@ -774,13 +767,23 @@ struct btf_ext *btf_ext__new(__u8 *data, __u32 size)
774
767
if (!btf_ext )
775
768
return ERR_PTR (- ENOMEM );
776
769
777
- err = btf_ext_copy_func_info (btf_ext , data , size );
778
- if (err ) {
779
- btf_ext__free (btf_ext );
780
- return ERR_PTR (err );
770
+ btf_ext -> data_size = size ;
771
+ btf_ext -> data = malloc (size );
772
+ if (!btf_ext -> data ) {
773
+ err = - ENOMEM ;
774
+ goto done ;
781
775
}
776
+ memcpy (btf_ext -> data , data , size );
782
777
783
- err = btf_ext_copy_line_info (btf_ext , data , size );
778
+ err = btf_ext_setup_func_info (btf_ext );
779
+ if (err )
780
+ goto done ;
781
+
782
+ err = btf_ext_setup_line_info (btf_ext );
783
+ if (err )
784
+ goto done ;
785
+
786
+ done :
784
787
if (err ) {
785
788
btf_ext__free (btf_ext );
786
789
return ERR_PTR (err );
@@ -789,6 +792,12 @@ struct btf_ext *btf_ext__new(__u8 *data, __u32 size)
789
792
return btf_ext ;
790
793
}
791
794
795
+ const void * btf_ext__get_raw_data (const struct btf_ext * btf_ext , __u32 * size )
796
+ {
797
+ * size = btf_ext -> data_size ;
798
+ return btf_ext -> data ;
799
+ }
800
+
792
801
static int btf_ext_reloc_info (const struct btf * btf ,
793
802
const struct btf_ext_info * ext_info ,
794
803
const char * sec_name , __u32 insns_cnt ,
@@ -837,15 +846,17 @@ static int btf_ext_reloc_info(const struct btf *btf,
837
846
return - ENOENT ;
838
847
}
839
848
840
- int btf_ext__reloc_func_info (const struct btf * btf , const struct btf_ext * btf_ext ,
849
+ int btf_ext__reloc_func_info (const struct btf * btf ,
850
+ const struct btf_ext * btf_ext ,
841
851
const char * sec_name , __u32 insns_cnt ,
842
852
void * * func_info , __u32 * cnt )
843
853
{
844
854
return btf_ext_reloc_info (btf , & btf_ext -> func_info , sec_name ,
845
855
insns_cnt , func_info , cnt );
846
856
}
847
857
848
- int btf_ext__reloc_line_info (const struct btf * btf , const struct btf_ext * btf_ext ,
858
+ int btf_ext__reloc_line_info (const struct btf * btf ,
859
+ const struct btf_ext * btf_ext ,
849
860
const char * sec_name , __u32 insns_cnt ,
850
861
void * * line_info , __u32 * cnt )
851
862
{
0 commit comments