@@ -598,17 +598,30 @@ impl PciHeader {
598
598
}
599
599
600
600
unsafe fn write < T > ( & self , offset : u32 , value : u32 ) {
601
+ let current = self . read :: < u32 > ( offset) ;
602
+
601
603
let bus = self . bus ( ) as u32 ;
602
604
let device = self . device ( ) as u32 ;
603
605
let func = self . function ( ) as u32 ;
606
+
604
607
let address = ( bus << 16 ) | ( device << 11 ) | ( func << 8 ) | ( offset & 0xFC ) | 0x80000000 ;
608
+ let noffset = ( offset & 0b11 ) * 8 ;
605
609
606
610
io:: outl ( PCI_CONFIG_ADDRESS_PORT , address) ;
607
-
608
611
match core:: mem:: size_of :: < T > ( ) {
609
- 1 => io:: outb ( PCI_CONFIG_DATA_PORT , value as u8 ) , // u8
610
- 2 => io:: outw ( PCI_CONFIG_DATA_PORT , value as u16 ) , // u16
611
- 4 => io:: outl ( PCI_CONFIG_DATA_PORT , value) , // u32
612
+ 1 => {
613
+ let mask = !( 0xffu32 << offset) ;
614
+ let value = ( current & mask) | ( ( value & 0xff ) << offset) ;
615
+ io:: outl ( PCI_CONFIG_DATA_PORT , value)
616
+ } // u8
617
+
618
+ 2 => {
619
+ let mask = !( 0xffffu32 << noffset) ;
620
+ let value = ( current & mask) | ( ( value & 0xffff ) << noffset) ;
621
+ io:: outl ( PCI_CONFIG_DATA_PORT , value)
622
+ } // u16
623
+
624
+ 4 => io:: outl ( PCI_CONFIG_DATA_PORT , value) , // u32
612
625
width => unreachable ! ( "unknown PCI write width: `{}`" , width) ,
613
626
}
614
627
}
0 commit comments