📄 ndiswrapper
字号:
if ($line =~ /([^=]+)=(.+)/) { return (trim($1), trim($2)); } else { return 0; }}sub choose_target_os { my @targets = @_; my $arch = `uname -m`; chomp($arch); printf DBG "arch: %s\n", $arch; if ($arch =~ /64$/) { $arch = "amd64"; } else { $arch = "x86"; } printf DBG "arch: %s\n", $arch; my @prefs = ("NT($arch)\.5\.1", "NT($arch)\.5", "NT($arch)", "NT\.5\.1", "NT\.5", "NT"); foreach my $pref (@prefs) { foreach my $target (@targets) { $target = trim($target); printf DBG "target: '%s', pref: '%s'\n", $target, $pref; if ($target =~ /NT((amd64)|(x86))/i) { printf DBG "target arch: '%s'\n", $1; next if ($1 !~ /$arch/i); } if ($target =~ /$pref/i) { return $target; } } } return "";}sub get_target_os_section { my ($section, $target) = @_; my $lines; chomp($section); $section =~ s/^\s*"\s*//; $section =~ s/\s*"\s*$//; printf DBG "section: \"%s\", target: \"%s\"\n", $section, $target; if (length($target) gt 0) { $lines = get_section($section . "." . $target); return $lines if ($lines); } my $arch = `uname -m`; chomp($arch); printf DBG "arch: %s\n", $arch; if ($arch =~ /64$/) { $arch = "AMD64"; } else { $arch = "X86"; } printf DBG "arch: %s\n", $arch; my @prefs = ("NT$arch.5.1", "NT$arch.5", "NT$arch", "NT.5.1", "NT.5", "NT"); foreach my $pref (@prefs) { $lines = get_section($section . "." . $pref); return $lines if ($lines); } $lines = get_section($section); return $lines if ($lines); printf DBG "couldn't find section \"$section\" for \"$arch\"\n"; return 0;}sub get_section_value { (my $section, my $name) = @_; return $parsed_sections{$section}->{$name};}sub get_string_value { my $key = shift; if ($key =~ /%(.+)%/) { $key = $1; return get_section_value("Strings", $key); } else { return $key; }}sub copy_file { my ($src, $dst) = @_; # ignore files not needed return 0 if (lc($src) =~ /\.((exe)|(dll)|(cpl)|(hlp))$/); my $real_file = get_file($src); if (length($real_file) gt 0) { $dst = lc($dst); printf DBG "copying \"$src_dir/$real_file\" to " . "\"$confdir/$driver_name/$dst\"\n"; copy("$src_dir/$real_file", "$confdir/$driver_name/$dst") or warn "couldn't copy \"$src_dir/$real_file\" to " . "\"$confdir/$driver_name\": $! -\n" . "installation may be incomplete\n"; printf DBG "chmod: $confdir/$driver_name/$dst\n"; chmod(0644, "$confdir/$driver_name/$dst"); if ($dst =~ /\.sys$/) { printf CONF "%s ", $dst; } } else { warn "couldn't find \"$src\" in \"$src_dir\"; make sure " . "all driver files, including .inf, .sys (and any firmware files) " . "are in \"$src_dir\" -\n" . "installation may be incomplete\n"; }}# for conf files with subvendor and subdevice, create conf files with just# vendor and devicesub create_fuzzy_conf { my $driver = shift; my $cwd = cwd(); chdir("$confdir/$driver") or die "couldn't chdir to $confdir/$driver: $!"; open(LS, "ls -1 . |") or die "couldn't open $confdir/$driver: $!"; while (my $file = <LS>) { chomp($file); if ($file =~ /$re_sub_dev_conf/) { my $fuzzy_file = "$1:$2.$5.conf"; printf DBG "file: $file, fuzzy file: $fuzzy_file\n"; if (! -e "$confdir/$driver/$fuzzy_file") { symlink("$file", "$fuzzy_file") or warn "couldn't link $confdir/$driver/$file " . "to $confdir/$driver/$fuzzy_file: $!\n"; } } } close(LS); chdir($cwd) or warn "couldn't chdir to $cwd: $!"; return 0;}# find a file in a case-insensitive way.sub get_file { my $file = lc(shift); if (opendir(DIR, "$src_dir")) { my @allfiles = readdir(DIR); foreach my $real_file (@allfiles) { if (lc($real_file) eq $file) { closedir(DIR); return $real_file; } } closedir(DIR); } else { warn "couldn't open \"$src_dir\": $! -\n" . "installation may be incomplete\n"; } return "";}sub strip_quotes { my $s = shift; $s =~ s/"(.*)"/$1/; return $s;}sub del_comment { my $s = shift; $s =~ s/;.*//; return $s;}# remove whitsepace at front and end.sub trim { my $s = shift; $s =~ s/^\s*//; $s =~ s/\s*$//; return $s;}sub valid_copy_file_name { my $file = shift; $file = lc($file); printf DBG "file name: %s\n", $file; foreach my $disk_file (@source_disks_files) { return 1 if ($file eq $disk_file); } # some inf files may not have SourceDisksFiles section, so use # known file names return 1 if ($file =~ /\.((sys)|(bin)|(out))$/); return 0;}sub parse_source_disks_files { my $lines = get_source_disks_files(); if ($lines) { foreach my $line (@{$lines}) { $line = del_comment($line); next if (length($line) eq 0); my @file = split("=", $line); next if (@file eq 0 or length($file[0] eq 0)); printf DBG "source disk file: \"%s\"\n", trim($file[0]); push (@source_disks_files, lc(trim($file[0]))); } } else { warn "couldn't find SourceDisksFiles section - " . "continuing anyway...\n"; }}sub get_source_disks_files { my $arch = `uname -m`; chomp($arch); if ($arch =~ /64$/) { $arch = "AMD64"; } else { $arch = "X86"; } my $lines = get_section("SourceDisksFiles." . $arch); return $lines if ($lines); $lines = get_section("SourceDisksFiles"); return $lines if ($lines); return 0;}sub device_driver_alias { my ($devid, $driver) = @_; my $done = 0; $devid = uc($devid); if (!($devid =~ /^$re_dev_id:$re_dev_id$/)) { printf "'$devid' is not a valid device ID\n"; return 1; } open(LS, "ls -1 $confdir/$driver/ |") or die "couldn't open $confdir/$driver: $!"; while (my $f = <LS>) { chomp($f); if ($f =~ /\.([[:xdigit:]]+)\.conf$/) { if (stat("$confdir/$driver/$devid.$1.conf")) { printf "Driver '$driver' is already used for '$devid'\n"; $done = 1; last; } if (symlink("$f", "$confdir/$driver/$devid.$1.conf")) { printf "WARNING: Driver '$driver' will be used for '$devid'\n" . "This is safe _only_ if driver $driver is meant for " . "chip in device $devid\n"; $done = 1; last; } else { warn "couldn't create symlink for \"$f\": $! -\n" . "installation may be incomplete\n"; } } } close(LS); if ($done == 0) { printf "driver '$driver' is not installed (properly)!\n"; return 1; } return 0;}sub generate_module_device_map { my $mode = shift; my ($vendor, $device, $subvendor, $subdevice, $bustype, $busid); my $device_map; if (-d "/etc/modprobe.d") { $device_map = $modconf; } elsif (-d "/etc/modules.d") { $device_map = "/etc/modules.d/ndiswrapper"; } else { $device_map = "/etc/ndiswrapper/ndiswrapper"; } open(DEVMAP, "| sort >$device_map") or die "couldn't create modules alias file $device_map: $!"; open(LS, "ls -1 $confdir|") or die "couldn't open $confdir: $!"; while (my $driver = <LS>) { chomp($driver); my $stat = (stat("$confdir/$driver"))[2]; if (S_ISDIR($stat)) { open(LS2, "ls -1 $confdir/$driver/ |") or die "couldn't open $confdir/$driver: $!"; while (my $file = <LS2>) { chomp ($file); if ($file =~ /\.conf$/) { if ($file =~ /^$re_sub_dev_conf$/) { ($vendor, $device, $subvendor, $subdevice, $busid) = (uc($1), uc($2), "0000$3", "0000$4", hex($5)); } elsif ($file =~ /^$re_dev_conf$/) { ($vendor, $device, $subvendor, $subdevice, $busid) = (uc($1), uc($2), "*", "*", hex($3)); } my $devstring; if ($busid eq $WRAP_USB_BUS or $busid eq 0) { $devstring = sprintf("usb:v%sp%sd*dc*dsc*dp*ic*isc*ip*", $vendor, $device); } elsif ($busid eq $WRAP_PCI_BUS) { $devstring = sprintf("pci:v0000%sd0000%ssv%ssd%sbc*sc*i*", $vendor, $device, $subvendor, $subdevice); } else { warn "wrong bustype ($busid) for " . "configuration file $file - ignoring it\n"; next; } if ($mode == 0) { printf DEVMAP "alias %s ndiswrapper\n", $devstring; } else { printf DEVMAP "install %s /sbin/modprobe ndiswrapper\n", $devstring; } } } close(LS2); } } close(LS); close(DEVMAP); printf "module configuration information is stored in $device_map\n"; return 0;}sub list_drivers { my $cards = get_cards(); open(LS, "ls -1 $confdir|") or die "couldn't open $confdir: $!"; while (my $driver = <LS>) { chomp($driver); if (-e "$confdir/$driver") { printf "%s : %s\n", $driver, install_status($cards, $driver); } } close(LS); return 0;}sub add_module_alias { my $alias = 0; open(MODPROBE, "modprobe -c|") or die "couldn't run modprobe: $!"; while (my $line = <MODPROBE>) { if ($line =~ /^alias\s.+\sndiswrapper/) { printf "module configuration already contains alias directive\n\n"; $alias = 1; } elsif ($line =~ /^install\s.*ndiswrapper/) { warn "module configuration contains directive $line;" . "you should delete that"; } elsif ($line =~ /^post-install\s+ndiswrapper/) { warn "module configuration contains directive $line;" . "you should delete that"; } } close(MODPROBE); if ($alias) { return 0; } printf "adding \"alias wlan0 ndiswrapper\" to $modconf ...\n"; system("echo \"alias wlan0 ndiswrapper\" >>$modconf") == 0 or die "couldn't add module alias: $!"; if (-x "/sbin/update-modules") { system("/sbin/update-modules"); } return 0;}sub get_cards {#01:00.0 Class 0300: 1002:4c66 (rev 01)# Subsystem: 1043:1732 my @cards = (); if (open(LSPCI, "lspci -vn|")) { my $card; while (my $line = <LSPCI>) { if ($line =~ /^[0-9a-f]+.+\s$re_dev_id:$re_dev_id/) { $card = {vendor => uc($1), device => uc($2)}; printf DBG "card: %s, %s\n", $1, $2; } elsif ($line =~ /.+Subsystem:\s$re_dev_id:$re_dev_id/) { $card->{subvendor} = uc($1); $card->{subdevice} = uc($2); printf DBG "sub: %s, %s\n", $1, $2; push(@cards, $card); } } close(LSPCI); } if (open(LSUSB, "lsusb |")) { my $card; while (my $line = <LSUSB>) { if ($line =~ /.+: ID\s$re_dev_id:$re_dev_id/) { $card = {vendor => uc($1), device => uc($2)}; push(@cards, $card); } } close(LSUSB); } return \@cards;}sub install_status { my ($cards, $driver) = @_; if (!$cards or !$driver) { return; } my ($sys, $conf, $inf); my ($vendor, $device, $subvendor, $subdevice, $busid, $ret); $sys = $conf = $inf = 0; open(LS2, "ls -1 $confdir/$driver|") or die "couldn't open $confdir/$driver: $!"; while (my $file = <LS2>) { chomp($file); if ($file =~ /\.sys$/) { $sys = 1; } elsif ($file =~ /\.inf$/) { $inf = 1; } elsif ($file =~ /^$re_sub_dev_conf$/) { $busid = hex($5); $conf = 1 if ($busid eq $WRAP_PCI_BUS); } elsif ($file =~ /^$re_dev_conf$/) { $busid = hex($3); $conf = 1 if ($busid eq $WRAP_USB_BUS or $busid eq 0 or $busid eq $WRAP_PCI_BUS); } } close(LS2); printf DBG "status: $sys, $inf, $conf\n"; if ($sys eq 0 or $inf eq 0 or $conf eq 0) { $ret = "invalid driver!"; return $ret; } $ret = "driver installed"; open(LS2, "ls -1 $confdir/$driver|") or die "couldn't open $confdir/$driver: $!"; while (my $file = <LS2>) { chomp($file); next if ($file !~ /\.conf$/); $conf = 0; if ($file =~ /^$re_sub_dev_conf$/) { ($vendor, $device, $subvendor, $subdevice, $busid) = (uc($1), uc($2), uc($3), uc($4), hex($5)); $conf = 1; foreach my $card (@{$cards}) { if ($card->{vendor} eq $vendor and $card->{device} eq $device and $card->{subvendor} eq $subvendor and $card->{subdevice} eq $subdevice and $busid eq $WRAP_PCI_BUS) { $ret .= "\n\tdevice ($vendor:$device" . ":$subvendor:$subdevice) present"; $conf = 2; last; } } } elsif ($file =~ /^$re_dev_conf/) { ($vendor, $device, $subvendor, $subdevice, $busid) = (uc($1), uc($2), "\\*", "\\*", hex($3)); $conf = 1; foreach my $card (@{$cards}) { if ($card->{vendor} eq $vendor and $card->{device} eq $device and ($busid eq $WRAP_USB_BUS or $busid eq 0 or $busid eq $WRAP_PCI_BUS)) { $ret .= "\n\tdevice ($vendor:$device) present"; $conf = 2; last; } } } next if ($conf le 1); # find if kernel knows of an alternate driver for this device my $devstring; if ($busid eq $WRAP_USB_BUS or $busid eq 0) { $devstring = sprintf("usb:v%sp%sd", $vendor, $device); } elsif ($busid eq $WRAP_PCI_BUS) { $devstring = sprintf("pci:v0000%sd0000%ssv", $vendor, $device); } else { next; } open(MODPROBE, "modprobe -c|") or next; while (my $line = <MODPROBE>) { my $alt; chomp($line); next if $line !~ /$devstring/; $alt = (split(' ', $line))[-1]; chomp($alt); if (length($alt) gt 0 and $alt ne "ndiswrapper") { $ret .= " (alternate driver: $alt)"; last; } } close(MODPROBE); } close(LS2); printf DBG "driver: $driver, $ret\n"; return $ret;}## Local Variables: #### cperl-indent-level: 4 #### End: ##
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -