Generated: Tue Feb 2 17:54:26 2010 from cmp2dsps.pl 2009/10/27 41.5 KB.
#!/perl -w # NAME: cmp2dsps.pl # AIM: Comparison of TWO DSP files - show different SOURCE files only ... # # 20090828 - BUG squashed ;=)) This was '$i1', which is WRONG $v6_srcs2[$i2][4] = $i1 + 1; # 20090827 - Some improvements in configuration compare # # 13/08/2008 geoff mclane http://geoffair.net/mperl # Only compares SOURCE lists. Still to compare config parameters ... use strict; use warnings; use File::Basename; use File::stat; # to get the file date require 'logfile.pl' or die "Unable to load logfile.pl ...\n"; # log file stuff my ($LF); my $pgmname = $0; if ($pgmname =~ /\w{1}:\\.*/) { my @tmpsp = split(/\\/,$pgmname); $pgmname = $tmpsp[-1]; } my $outfile = "temp.$pgmname.txt"; open_log($outfile); ### prt( "$0 ... Hello, World ...\n" ); # options my $minlen1 = 40; my $minlen2 = 64; my $compconfig = 1; # not completed - compare config stuff my $dbg_dsp = 0; my $dbg_ds1 = 0; my $dbg_ds2 = 0; my $dbg_ds3 = 0; my $dbg_ds4 = 0; # show CPP and LINK config items - %v6_conf my $dbg_ds5 = 0; # show Defined items - %v6_defs my $dbg_ds6 = 0; # show !IF, !ELSEIF switching my $dbg_ds7 = 0; # show %v6_conf listing my $big_dbg = 0; my $dbg_ds8 = 0; # show VC6 Filter and Group Name my $dbg_ds9 = 0; # show EACH VC6 source pushed my $dbg_ds10 = 0; # show prt( "NO MATCH of 1 [$ff1] in 2\n" ) if ($dbg_ds10); # compiler flags my %compile_flags = ( 'nologo' => 0, 'W3' => 0, 'Gm' => 0, 'GR' => 0, 'GX' => 0, 'ZI' => 0, 'Od' => 0, 'MTd' => 0, 'I' => 1, 'D' => 1, 'FD' => 0, 'GZ' => 0, 'c' => 0, 'O2' => 0, 'MT' => 0 ); my @warnings = (); my @v6_srcs = (); # relnm full group filter my %v6_defs = (); my %v6_conf = (); # file 1 stuff my @v6_srcs1 = (); # relnm full group filter my %v6_defs1 = (); my %v6_conf1 = (); # file 2 stuff my @v6_srcs2 = (); # relnm full group filter my %v6_defs2 = (); my %v6_conf2 = (); my $in_file1 = 'temp.testcon.dsp'; my $in_file2 = 'tempdsp3.dsp'; my $root_dir = '.'; my $projname = 'testcon'; #my $in_file1 = 'temp.libavcodec.dsp'; #my $in_file2 = 'C:\Projects\hb\ffmpeg\build\msvc\libavcodec.dsp'; #my $root_dir = 'C:\Projects\hb\ffmpeg\build\msvc'; #my $projname = 'libavcodec'; #my $in_file1 = 'temp.Map.dsp'; #my $in_file2 = 'C:\FG\27\Atlas-04\build\msvc\Map.dsp'; #my $in_file1 = 'temp.Atlas.dsp'; #my $in_file2 = 'C:\FG\27\Atlas-04\build\msvc\Atlas.dsp'; #my $root_dir = 'C:\FG\27\Atlas-04\build\msvc'; #my $projname = 'Atlas'; #my $in_file1 = 'temp.#Win32.libtar.dsp'; #my $in_file2 = 'C:\Projects\tar120\Win32\libtar.dsp'; #my $root_dir = "C:\\Projects\\tar120\\Win32\\"; #my $projname = 'libtar'; #my $in_file1 = 'temp.xmlrpc.dsp'; #my $in_file2 = 'C:\FG\FGCOMXML\xmlrpc-c\Windows\xmlrpc.dsp'; #my $root_dir = "C:\\FG\\FGCOMXML\\xmlrpc-c\\Windows\\"; #my $projname = 'xmlrpc'; my @discarded_dupes = (); my @lines1 = (); my @lines2 = (); my $lncnt1 = 0; my $lncnt2 = 0; sub clear_load { @v6_srcs = (); # relnm full group filter %v6_defs = (); %v6_conf = (); } sub process_DSP { my ($proj, $fil) = @_; my ($line, $prjname, $grpname, $filter, $ff, $src, $chr, $tmp, $conf, $ffnr); my ($itm1, $itm2, $key, $targtype, $i); my $scnt = 0; my @dsp_lines = (); my %src_list = (); # 20090828 - avoid adding simple DUPLICATES my $inanif = 0; # in an !IF block my $ins = 0; # in a source block my $inproj = 0; # in project portion of file my $intarget = 0; my $ingroup = 0; my $incustom = 0; my $sline = ''; my $inspecial = 0; my %prop_nh = (); my %add_nh = (); my @tmparr = (); my ($item); prt( "\nProcess DSP file $fil ... " ); if ( -f $fil ) { my $sb = stat($fil); prt( "dated ".scalar localtime($sb->mtime).", size ".$sb->size." bytes.\n" ); my ($name,$dir) = fileparse($fil); $dir = trim_all($dir); $dir = $root_dir if ((length($dir) == 0)||($dir eq ".\\")); $dir .= "\\" if !($dir =~ /[\\\/]$/); # 20090827 - ensure ends with '\' if ( open IF, "<$fil" ) { @dsp_lines = <IF>; close IF; my $lncnt = scalar @dsp_lines; prt( "Got $lncnt lines, from file [$fil], to process ...\n" ); for ($i = 0; $i < $lncnt; $i++) { $line = $dsp_lines[$i]; $line = trim_all($line); next if (length($line) == 0); $chr = substr($line, 0, 1); # get FIRST char of LINE if( $chr eq '#' ) { # line begins with SHARP $sline = trim_all(substr($line,1)); # [# Microsoft Developer Studio Project File - Name="" - Package Owner=<4>] # if ($line =~ /\s+Microsoft Developer Studio Project File - Name=\"([\.\w\s]+)+/) { if ($line =~ /\s+Microsoft Developer Studio Project File - Name="([\.\w\s]+)*" - Package/) { $prjname = $1; $prjname = '<no project name>' if (length($prjname) == 0); $v6_defs{'PROJECT_NAME'} = $prjname; prt( "Project NAME = [$prjname]\n" ); # if ($dbg_dsp); } elsif ($line =~ /\s+Microsoft Developer Studio Generated Build File, Format Version ([\d\.]+)/) { prt( "dbg_dsp: MSVC Version $1 ...\n" ) if ($dbg_dsp); #} elsif ($line =~ /\s*TARGTYPE\s+\"(.+)\"\s+/) { # Win32 (x86) Console Application" 0x0103 } elsif ($line =~ /\s*TARGTYPE\s+"(.+)"\s+/) { # Win32 (x86) Console Application" 0x0103 $targtype = $1; prt( "TARGTYPE: [$targtype], name=[$prjname] ($proj)\n" ); $v6_defs{'PROJECT_TYPE'} = $targtype; } elsif ($sline =~ /^PROP\s+/) { $sline =~ s/^PROP\s+//; $sline =~ s/^BASE\s+//; if ($line =~ /PROP\s+Default_Filter\s+\"([\w;]+)+\"/ ) { $filter = $1; prt( "dbg_ds8: Begin Filter group $grpname, filter $filter\n" ) if ($dbg_ds8); } elsif ($sline =~ /^Use_MFC/) { # *TBD* if needed } elsif ($sline =~ /^Scc_ProjName/) { # *TBD* if needed } elsif ($sline =~ /^AllowPerConfigDependencies/) { # *TBD* if needed } elsif ($sline =~ /^Output_Dir/) { # *TBD* if needed } elsif ($sline =~ /^Scc_LocalPath/) { # *TBD* if needed } elsif ($sline =~ /^Intermediate_Dir/) { # *TBD* if needed } elsif ($sline =~ /^Use_Debug_Libraries/) { # *TBD* if needed } elsif ($sline =~ /^Ignore_Export_Lib/) { # *TBD* if needed } elsif ($sline =~ /^Exclude_From_Build/) { # *TBD* if needed } elsif ($sline =~ /^Target_Dir/) { # *TBD* if needed } else { prtw( "WARNING: PROP NOT HANDLED! [$sline] [$line]\n" ); @tmparr = split(/\s/,$sline); $item = $tmparr[0]; $prop_nh{$item} = 1; } } elsif ( $sline =~ /^ADD\s+/ ) { $sline =~ s/^ADD\s+//; $sline =~ s/^BASE\s+//; if ( $line =~ /ADD BASE CPP (.+)/ ) { $item = $1; # ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /Yu"stdafx.h" /FD /c $key = 'CPP '.$conf; prt( "dbg_ds4: ADD BASE key=[$key] [$item]\n" ) if ($dbg_ds4); $v6_conf{$key} = $item; } elsif ( $line =~ /ADD CPP (.+)/ ) { $item = $1; # ADD CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /FD /c $key = 'CPP '.$conf; prt( "dbg_ds4: ADD key=[$key] [$item]\n" ) if ($dbg_ds4); $v6_conf{$key} = $item; } elsif ( $line =~ /ADD BASE LINK32 (.+)/ ) { $item = $1; # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /machine:I386 $key = 'LINK '.$conf; prt( "dbg_ds4: ADD BASE key=[$key] [$item]\n" ) if ($dbg_ds4); $v6_conf{$key} = $item; } elsif ( $line =~ /ADD LINK32 (.+)/ ) { $item = $1; $key = 'LINK '.$conf; # ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /machine:I386 prt( "dbg_ds4: ADD key=[$key] [$item]\n" ) if ($dbg_ds4); $v6_conf{$key} = $item; } elsif ($sline =~ /^RSC/) { # *TBD* if needed } elsif ($sline =~ /^BSC32/) { # *TBD* if needed } else { prtw( "WARNING: ADD NOT HANDLED! [$sline] [$line]\n" ); @tmparr = split(/\s/,$sline); $item = $tmparr[0]; $add_nh{$item} = 1; } } elsif ( $sline =~ /\*\*\s+DO\s+NOT\s+EDIT\s+\*\*/) { # ignore this line } elsif ( $sline =~ /^Name\s+(.+)$/) { # Name "testcon - Win32 ReleaseSSE"] } elsif ( $sline =~ /^SUBTRACT\s+/ ) { # ignore for now } elsif ( $line =~ /Begin\s+Project/ ) { $inproj = 1; } elsif ( $line =~ /End\s+Project/ ) { $inproj = 0; } elsif ( $line =~ /Begin\sTarget/ ) { $intarget = 1; } elsif ( $line =~ /End\sTarget/ ) { $intarget = 0; } elsif ($line =~ /Begin Group \"([\s\w]+)+/ ) { $grpname = $1; prt( "dbg_dsp: Begin group ... $grpname\n" ) if ($dbg_dsp); $ingroup = 1; } elsif ($line =~ /End\s+Group/) { $ingroup = 0; } elsif ($line =~ /Begin\s+Source\s+File/) { $ins = 1; prt( "dbg_dsp: Begin source ... $ins ...\n" ) if ($dbg_dsp); } elsif ($line =~ /End\s+Source\s+File/) { $ins = 0; prt( "dbg_dsp: End source ... $ins ...\n" ) if ($dbg_dsp); } elsif ($line =~ /Begin\s+Custom\s+Build/) { $incustom = 1; } elsif ($line =~ /End\s+Custom\s+Build/) { $incustom = 0; } elsif ($line =~ /Begin\s+Special\s+Build\s+Tool/) { $inspecial = 1; } elsif ($line =~ /End\s+Special\s+Build\s+Tool/) { $inspecial = 0; } else { prtw( "WARNING: Line beginning with SHARP(#) NOT HANDLED [$line]\n" ); } } elsif ( $chr eq '!' ) { # line beginning with '!' char $sline = substr($line,1); if ($line =~ /^!IF\s+(.+)/i ) { prt( "dbg_ds6: Entering IF $1 ...\n" ) if ($dbg_ds6); prtw( "WARNING: !IF found BUT aready in an !IF block!\n" ) if ( $inanif ); $inanif = 1; if ($line =~ /!IF\s+(.+) == (.+)/i) { $itm1 = $1; $itm2 = $2; $itm1 =~ s/\"//g; $itm2 =~ s/\"//g; prt( "dbg_ds6: Got [$itm1] [$itm2]...\n" ) if ($dbg_ds6); if ($itm1 =~ /^\$\((.+)\)/ ) { if (defined $v6_defs{$1}) { if ($v6_defs{$1} eq $itm2) { $tmp = "TRUE"; } else { $tmp = "FALSE"; } if( $1 eq 'CFG' ) { $conf = $itm2; } prt( "dbg_ds6: and [$1] defined as \"$v6_defs{$1}\" ... $tmp $conf\n" ) if ($dbg_ds6); } else { prt( "NOT DEFINED [$1] ...\n" ); } } } else { prt( "FAILED IF == [$line]\n" ); } } elsif ( $line =~ /^!ELSE\s+/i ) { prt( "dbg_ds6: Entering ELSE ...\n" ) if ($dbg_ds6); prtw( "WARNING: !ELSE found NOT in an !IF block!\n" ) if ( ! $inanif ); } elsif ( $line =~ /^!ELSEIF\s+(.+)/i ) { prt( "dbg_ds6: Entering ELSEIF $1 ...\n" ) if ($dbg_ds6); prtw( "WARNING: !ELSEIF found NOT in an !IF block!\n" ) if ( ! $inanif ); if ($line =~ /!ELSEIF\s+(.+) == (.+)/i) { $itm1 = $1; $itm2 = $2; $itm1 =~ s/\"//g; $itm2 =~ s/\"//g; prt( "dbg_ds6: Got [$itm1] [$itm2]...\n" ) if ($dbg_ds6); if ($itm1 =~ /^\$\((.+)\)/ ) { if (defined $v6_defs{$1}) { if ($v6_defs{$1} eq $itm2) { $tmp = "TRUE"; } else { $tmp = "FALSE"; } if( $1 eq 'CFG' ) { $conf = $itm2; } prt( "dbg_ds6: and [$1] defined as \"$v6_defs{$1}\" ... $tmp $conf\n" ) if ($dbg_ds6); } else { prt( "NOT DEFINED [$1] ...\n" ); } } } else { prt( "FAILED ELSEIF == [$line]\n" ); } } elsif ( $line =~ /^!ENDIF\s*/i ) { prt( "dbg_ds6: Out ENDIF ...\n" ) if ($dbg_ds6); prtw( "WARNING: !ENDIF found NOT in an !IF block!\n" ) if ( ! $inanif ); $inanif = 0; # end the !IF } elsif ( $line =~ /^!MESSAGE/) { # ignore MESSAGE lines for now... } else { prtw( "WARNING: Line beginning with ! NOT HANDLED [$line]\n" ); } } else { if ($line =~ /SOURCE=([\.\\\w-]+)+/ ) { $src = $1; ### $dir .= "\\" if !($dir =~ /[\\\/]$/); # 20090827 - ensure ends with '\' $ff = $dir.$src; $ffnr = fix_rel_path($ff); ###prt( "fixed=$ffnr, src=[$src], dir=[$dir]\n" ); if ($ins) { # had 'Begin Source File', and before 'End Source File' in DSP prt( "dbg_dsp: SOURCE = $src ($ff)... $ins \n" ) if ($dbg_dsp); } else { prt( "source = $src ($ff) OUTSIDE 'in source' ... $ins\n" ); } if (is_c_source($src)) { prt("dbg_ds1: SOURCE=[$src]\n") if ($dbg_ds1); } elsif (is_h_source($src)) { prt("dbg_ds2: HEADER=[$src]\n") if ($dbg_ds2); } elsif (is_h_special($src)) { prt("dbg_ds2: HEADER=[$src]\n") if ($dbg_ds2); } else { prt("dbg_ds3: OTHER=[$src]\n") if ($dbg_ds3); } if (defined $src_list{$src}) { prtw( "WARNING: Avoiding DUPLICATED SOURCE [$src]\n" ); # 20090828 - do NOT add duplicates } else { $src_list{$src} = 1; # 0 1 2 3 4 5 6 #push(@v8_srcs,[$src, $ffnr, $filtname, $filttype, 0, 0, $projname] ); push(@v6_srcs, [$src, $ffnr, $grpname, $filter, 0, 0, $proj] ); $scnt++; prt( "dbg_ds9: $scnt v6_srcs: $src, $ffnr, $grpname, $filter, 0, 0, $proj\n" ) if ($dbg_ds9); } } elsif ( $line =~ /(.*)=(.*)/ ) { $itm1 = $1; $itm2 = $2; $v6_defs{$itm1} = $itm2; prt( "dbg_ds5: Defined [$itm1] = [$itm2] ...\n" ) if ($dbg_ds5); } else { if ($incustom) { # just a custom build line } else { prtw( "WARNING: Skipped line [$line]\n" ); } } } } prt( "End DSP - got $scnt source files ...\n" ); if ($dbg_ds7) { foreach $key (keys %v6_conf) { prt( "Config $key = [$v6_conf{$key}]\n" ); } } @tmparr = keys(%prop_nh); if (@tmparr) { prt( "PROPs NOT HANDLED...\n" ); foreach $key (@tmparr) { prt( "elsif (\$sline =~ /^$key/) {\n" ); } } @tmparr = keys(%add_nh); if (@tmparr) { prt( "ADDs NOT HANDLED...\n" ); foreach $key (@tmparr) { prt( "elsif (\$sline =~ /^$key/) {\n" ); } } } else { prt( "ERROR: FAILED TO OPEN $fil FILE!\n" ); } } else { prt( "*** DOES NOT EXIST ***\n" ); exit(1); } } ############################################################################### sub fix_rel_path { my ($path) = shift; my @a = split(/\\/, $path); my $npath = ''; my $max = scalar @a; my @na = (); for (my $i = 0; $i < $max; $i++) { my $p = $a[$i]; if ($p eq '.') { # ignore this } elsif ($p eq '..') { if (@na) { pop @na; # discard previous } else { prt( "WARNING: Got relative .. without previous!!! path=$path\n" ); } } else { push(@na,$p); } } foreach my $pt (@na) { $npath .= "\\" if length($npath); $npath .= $pt; } return $npath; } ### utitlity subs sub is_c_source { my $f = shift; if ( ($f =~ /\.c$/i) || ($f =~ /\.cpp$/i) || ($f =~ /\.cxx$/i) ) { return 1; } ##if (!is_h_source($f)) { ## prt( "Item [$f] IS NOT C/C++ SOURCE!\n" ); ##} return 0; } sub is_h_special { my $f = shift; if (($f =~ /osg/i)||($f =~ /OpenThreads/i)||($f =~ /Producer/i)) { return 1; } return 0; } sub is_h_source { my $f = shift; if ( ($f =~ /\.h$/i) || ($f =~ /\.hpp$/i) || ($f =~ /\.hxx$/i) ) { return 1; } ##if (!is_c_source($f)) { ## prt( "Item [$f] IS NOT C/C++ SOURCE!\n" ); ##} return 0; } sub compare_defines_for { my ($src, $v1, $v2) = @_; if ($v1 eq $v2) { return 1; } return 0; } sub not_in_arrayi { my ($t,@a) = @_; my $lct = lc($t); foreach my $i (@a) { my $lci = lc($i); if ($lct eq $lci) { return 0; } } return 1; } sub ensure_unique { my (@ba) = @_; my @na = (); foreach my $itm (@ba) { if ( not_in_arrayi($itm,@na) ) { push(@na,$itm); # store new unique item } elsif ( not_in_arrayi($itm,@discarded_dupes) ) { push(@discarded_dupes,$itm); } } return @na; } sub space_split_with_quotes { my ($txt) = shift; my @a = (); my $ll = length($txt); my ($j, $c, $wd, $inq, $pc); $wd = ''; $inq = 0; $c = ''; for ($j = 0; $j < $ll; $j++) { $pc = $c; $c = substr($txt,$j,1); #// char by char if ($inq) { $inq = 0 if ($c eq '"'); } elsif ($c eq '"') { $inq = 1; } if ($c =~ /\s/) { # if a SPACEY char if ($inq) { $wd .= $c; # keep spaces, if IN double quotes } else { push(@a,$wd) if length($wd); # stack word, if any $wd = ''; # and clear word } } else { $wd .= $c; # store it } } return @a; } sub cmp_sw_hashes { my ($src, $rh1, $rh2 ) = @_; my ($ct1,$ct2, $key, $val1, $val2, $val11, $val22, $fnd); $ct1 = scalar keys(%{$rh1}); $ct2 = scalar keys(%{$rh2}); prt( "Compare switch hashes $ct1 vs $ct2 for [$src]\n" ); foreach $key (keys %{$rh1}) { if (defined ${$rh2}{$key}) { $val1 = ${$rh1}{$key}; $val2 = ${$rh2}{$key}; if (($key eq 'D')||($key eq 'I')) { # got an array of items $ct1 = scalar @{$val1}; $ct2 = scalar @{$val2}; if ($ct1 != $ct2) { prt( "Switch $key: items $ct1 vs $ct2...\n" ); } foreach $val11 (@{$val1}) { $fnd = 0; foreach $val22 (@{$val2}) { if ($val11 eq $val22) { $fnd = 1; last; } } if (!$fnd) { prt( "Switch $key: item [$val11] NOT found in 2...\n" ); } } foreach $val22 (@{$val2}) { $fnd = 0; foreach $val11 (@{$val1}) { if ($val11 eq $val22) { $fnd = 1; last; } } if (!$fnd) { prt( "Switch $key: item [$val22] NOT found in 1...\n" ); } } } } else { prt( "Key [$key] in 1, but NOT in 2\n" ); } } foreach $key (keys %{$rh2}) { if (!defined ${$rh1}{$key}) { prt( "Key [$key] in 2, but NOT in 1\n" ); } } } sub compare_configs_for { my ($src, $v1, $v2) = @_; my ($ct1, $ct2, $i, $j, $it1, $val1, $it2, $val2, $fnd); my (@sar1, @sar2, @a); # try for an easy compare if ($v1 eq $v2) { return 1; } # need to break up the config, and compare each items #my @ar1 = split(/\s/,$v1); #my @ar2 = split(/\s/,$v2); my @ar1 = space_split_with_quotes($v1); my @ar2 = space_split_with_quotes($v2); if ($src =~ /^LINK\s+/) { #prt( "Config compare diff get uniques ..." ); @ar1 = ensure_unique(@ar1); @ar2 = ensure_unique(@ar2); #prt( "done\n" ); } elsif ($src =~ /^CPP\s+/) { $ct1 = scalar @ar1; $ct2 = scalar @ar2; $fnd = 0; my %h1 = (); my %h2 = (); prt("Doing switch hashes... src[$src]\n" ); for ($i = 0; $i < $ct1; $i++) { $it1 = $ar1[$i]; if ($it1 =~ /^[\/-]{1}/) { $it2 = substr($it1,1); if (defined $compile_flags{$it2}) { if ($compile_flags{$it2}) { $i++; # take next if (defined $h1{$it2}) { $val1 = $h1{$it2}; push(@{$val1}, $ar1[$i]); $h1{$it2} = $val1; } else { @a = (); push(@a, $ar1[$i]); $h1{$it2} = [@a]; } } else { if (defined $h1{$it2}) { prt( "Repeated switch [$it2]\n" ); $h1{$it2}++; } else { $h1{$it2} = 1; } } } else { prt("WHAT is THIS switch [$it1]?\n"); } } else { prt("WHAT is THIS [$it1] non switch?\n"); } } for ($j = 0; $j < $ct2; $j++) { $it1 = $ar2[$j]; if ($it1 =~ /^[\/-]{1}/) { $it2 = substr($it1,1); if (defined $compile_flags{$it2}) { if ($compile_flags{$it2}) { $j++; # take next if (defined $h2{$it2}) { $val1 = $h2{$it2}; push(@{$val1}, $ar2[$j]); $h2{$it2} = $val1; } else { @a = (); push(@a, $ar2[$j]); $h2{$it2} = [@a]; } } else { if (defined $h2{$it2}) { prt( "Repeated switch [$it2]\n" ); $h2{$it2}++; } else { $h2{$it2} = 1; } } } else { prt("WHAT is THIS switch [$it1]?\n"); } } else { prt("WHAT is THIS [$it1] non switch?\n"); } } prt("Done switch hashes... src[$src]\n" ); cmp_sw_hashes( $src, \%h1, \%h2 ); } @sar1 = sort @ar1; @sar2 = sort @ar2; $ct1 = scalar @sar1; $ct2 = scalar @sar2; if ($ct1 != $ct2) { prt( "src=[$src] Diff array lengths $ct1 vs $ct2 ... line len ".length($v1)." vs ".length($v2)." chars\n" ); } #prt( "Config compare diff length $ct1 ...\n" ); for ($ct1 = 0; $ct1 < $ct2; $ct1++) { my $lc1 = lc($sar1[$ct1]); my $lc2 = lc($sar2[$ct1]); if ($lc1 ne $lc2) { prt( "src=[$src] Config compare diff [$lc1] with [$lc2] ...\n" ); return 0; } } # everything is the SAME (except maybe for case, and duplicates)... return 1; } sub show_link_diff { my ($cnt, $src, $v1, $v2) = @_; my ($ct1, $ct2); prt( "$cnt:1: $src = $v1\n" ); prt( "$cnt:2: $src = $v2\n" ); my @notin2 = (); my @notin1 = (); my @ar1 = split(/\s/,$v1); my @ar2 = split(/\s/,$v2); if ($src =~ /^LINK\s+/) { #prt( "Config compare diff get uniques ..." ); @ar1 = ensure_unique(@ar1); @ar2 = ensure_unique(@ar2); #prt( "done\n" ); } my @sar1 = sort @ar1; my @sar2 = sort @ar2; $ct1 = scalar @sar1; $ct2 = scalar @sar2; #prt( "Config compare diff length $ct1 ...\n" ); for ($ct2 = 0; $ct2 < $ct1; $ct2++) { my $lc1 = lc($sar1[$ct2]); if ( not_in_arrayi($lc1,@sar2) ) { if ( not_in_arrayi($lc1,@notin2) ) { push(@notin2,$sar1[$ct2]); } } } $ct2 = scalar @sar2; for ($ct1 = 0; $ct1 < $ct2; $ct1++) { my $lc2 = lc($sar2[$ct1]); if ( not_in_arrayi($lc2,@sar1) ) { if ( not_in_arrayi($lc2,@notin1) ) { push(@notin1,$sar2[$ct1]); } } } if (@notin2) { prt("Found ".join(" ",@notin2)." in 1, not in 2\n"); } if (@notin1) { prt("Found ".join(" ",@notin1)." in 2, not in 1\n"); } } sub show_link_diff_simp { my ($cnt, $src, $v1, $v2) = @_; prt( "L:$cnt:1: $src = $v1\n" ); prt( "L:$cnt:2: $src = $v2\n" ); } sub get_dsp_block { my ($src) = shift; my $dsp = <<EOF; # Begin Source File SOURCE=$srcc # End Source File EOF return $dsp; } sub compare_dsp_with_dsp { my ($file1,$file2) = @_; my ($i1, $i2, $fnd, $matched); my ($src1, $ff1, $fnm1, $typ1, $flg1); my ($src2, $ff2, $fnm2, $typ2, $flg2); my ($nm1, $pth1, $suf1); my ($nm2, $pth2, $suf2); my ($added, $subed, $miss1, $miss2, $min, $adddsp, $extra_dbg); my $msg = ''; $extra_dbg = 0; # compare SOURCES ############################### my $v6_tot1 = scalar @v6_srcs1; my $v6_tot2 = scalar @v6_srcs2; prt( "\nCompare of sources MSVC6 totals $v6_tot1, with $v6_tot2 ...\n" ); $fnd = 0; $matched = 0; for ($i1 = 0; $i1 < $v6_tot1; $i1++) { $v6_srcs1[$i1][4] = 0; # clear matched } for ($i2 = 0; $i2 < $v6_tot2; $i2++) { $v6_srcs2[$i2][4] = 0; # clear matched } # for EACH in file 1 # ==================== for ($i1 = 0; $i1 < $v6_tot1; $i1++) { $src1 = $v6_srcs1[$i1][0]; $ff1 = $v6_srcs1[$i1][1]; $fnm1 = $v6_srcs1[$i1][2]; $typ1 = $v6_srcs1[$i1][3]; $flg1 = $v6_srcs1[$i1][4]; $fnd = 0; # extra #if ($src1 =~ /colorspace/) { # prt("extra_dbg: Doing file [$ff1]...\n"); # $extra_dbg = 1; #} # --------------- # find in file2 # ============= for ($i2 = 0; $i2 < $v6_tot2; $i2++) { $src2 = $v6_srcs2[$i2][0]; $ff2 = $v6_srcs2[$i2][1]; $fnm2 = $v6_srcs2[$i2][2]; $typ2 = $v6_srcs2[$i2][3]; $flg2 = $v6_srcs2[$i2][4]; #if (is_same_file($ff1,$ff2)) { if ( is_same_source_file($ff1,$ff2) ) { $v6_srcs2[$i2][4] = $i1 + 1; # 20090828 - This was '$i1', which is WRONG $v6_srcs1[$i1][4] = $i2 + 1; $fnd = 1; last; } } if ($extra_dbg) { prt( "extra_dbg: Find = $fnd - offsets $i1 of $v6_tot1, $i2 of $v6_tot2...\n" ); $extra_dbg = 0; } if ($fnd) { $matched++; } else { prt( "dbg_ds10: NO MATCH of 1 [$ff1] in 2!\n" ) if ($dbg_ds10); } } $added = $v6_tot1 - $matched; $subed = $v6_tot2 - $matched; prt( "In the compare of -\n" ); prt( "FILE1: [$file1] $v6_tot1 sources, with\n" ); prt( "FILE2: [$file2] $v6_tot2 sources...\n" ); prt( "Matched $matched of $v6_tot1, with $matched of $v6_tot2 ...\n" ); # get sources NOT matched in file1 $miss1 = 0; for ($i1 = 0; $i1 < $v6_tot1; $i1++) { if ($v6_srcs1[$i1][4] == 0) { $miss1++; } } if ($miss1) { prt( "MISSED1: [$file1] contains $miss1, NOT in file 2 ...\n" ); for ($i1 = 0; $i1 < $v6_tot1; $i1++) { if ($v6_srcs1[$i1][4] == 0) { $src1 = $v6_srcs1[$i1][0]; $ff1 = $v6_srcs1[$i1][1]; $msg = "$src1 "; $min = $minlen1; $msg .= ' ' while (length($msg) < $min); $msg .= "($ff1) "; $min += 3 + $minlen2; $msg .= ' ' while (length($msg) < $min); if (-f $ff1) { $msg .= "ok"; } else { $msg .= "MISSING?"; } prt( "$msg\n" ); } } } else { prt( "NONE: [$file1] list has no missed files...\n" ); } # get sources NOT matched in file2 $miss2 = 0; for ($i2 = 0; $i2 < $v6_tot2; $i2++) { if ($v6_srcs2[$i2][4] == 0) { $miss2++; } } if ($miss2) { prt( "\nMISSED2: [$file2] contains $miss2, NOT in file 1 ...\n" ); $adddsp = ''; for ($i2 = 0; $i2 < $v6_tot2; $i2++) { if ($v6_srcs2[$i2][4] == 0) { $src2 = $v6_srcs2[$i2][0]; $ff2 = $v6_srcs2[$i2][1]; $msg = "$src2 "; $min = $minlen1; $msg .= ' ' while (length($msg) < $min); $msg .= "($ff2) "; $min += 3 + $minlen2; $msg .= ' ' while (length($msg) < $min); if (-f $ff2) { $msg .= "ok"; $adddsp .= get_dsp_block($src2); } else { $msg .= "MISSING?"; } prt( "$msg\n" ); } } if (length $adddsp) { prt( "Suggested ADDITIONS to $file1...\nbut take care they are not included in other files if C source\n$adddsp" ); } } else { prt( "\nNONE: [$file2] list has no missed files...\n" ); } prt("\n"); if ($compconfig) { # also should COMPARE # %v6_defs1 with %v6_defs2, and # %v6_conf1 with %v6_conf2 my ($val1, $val2, $tcnt, $cnt); my $samecount = 0; my $missingcount = 0; my $isthesame = 0; my %done1 = (); my %done2 = (); $tcnt = scalar keys(%v6_defs1); prt("Compare of $tcnt defines...\n"); $cnt = 0; foreach $src1 (keys %v6_defs1) { $cnt++; $val1 = $v6_defs1{$src1}; if (defined $v6_defs2{$src1}) { $val2 = $v6_defs2{$src1}; if (compare_defines_for($src1, $val1, $val2)) { # prt( "$cnt: $src1 = $val1 and value 2 is the same\n" ); $samecount++; } else { # prt( "$cnt:1: $src1 = $val1\n" ); # prt( "$cnt:2: $src1 = $val2\n" ); } $done1{$src1} = 1; } else { # prt( "$cnt:1: $src1 = $val1\n" ); # prt( "$cnt:2: $src1 = NOT AVAILABLE\n" ); $missingcount++; } } $isthesame = 1 if ($cnt == $samecount); if ($isthesame) { prt("End compare of $tcnt defines, and THEY are the same...\n"); } else { $cnt = 0; foreach $src1 (keys %v6_defs1) { $cnt++; $val1 = $v6_defs1{$src1}; if (defined $v6_defs2{$src1}) { $val2 = $v6_defs2{$src1}; if (compare_defines_for($src1, $val1, $val2)) { prt( "$cnt: $src1 = $val1 and value 2 is the same\n" ); $samecount++; } else { prt( "$cnt:1: $src1 = $val1\n" ); prt( "$cnt:2: $src1 = $val2\n" ); } $done1{$src1} = 1; } else { prt( "$cnt:1: $src1 = $val1\n" ); prt( "$cnt:2: $src1 = NOT AVAILABLE\n" ); $missingcount++; } } } foreach $src2 (keys %v6_defs2) { if ( ! defined $done1{$src2}) { $val2 = $v6_defs2{$src1}; prt( "M2: $src1 = $val2\n" ); } } $tcnt = scalar keys(%v6_conf1); prt("Compare of $tcnt config items...\n"); $samecount = 0; $missingcount = 0; $isthesame = 0; $cnt = 0; foreach $src1 (keys %v6_conf1) { $cnt++; $val1 = $v6_conf1{$src1}; if (defined $v6_conf2{$src1}) { $val2 = $v6_conf2{$src1}; if (compare_configs_for($src1, $val1, $val2)) { #prt( "$cnt: $src1 = $val1,\nand value 2 is the SAME!\n" ); $samecount++; } else { if ($src1 =~ /^LINK\s+/) { show_link_diff($cnt, $src1, $val1, $val2); } else { #prt( "$cnt:1: $src1 = $val1\n" ); #prt( "$cnt:2: $src1 = $val2\n" ); } } $done2{$src1} = 1; } else { #prt( "$cnt:1: $src1 = $val1\n" ); #prt( "$cnt:2: $src1 = NOT AVAILABLE\n" ); $missingcount++; } } $isthesame = 1 if ($cnt == $samecount); if ($isthesame) { prt("End compare of $tcnt config items, and THEY are the same...\n"); } else { $cnt = 0; foreach $src1 (keys %v6_conf1) { $cnt++; $val1 = $v6_conf1{$src1}; if (defined $v6_conf2{$src1}) { $val2 = $v6_conf2{$src1}; if (compare_configs_for($src1, $val1, $val2)) { prt( "$cnt: $src1 = $val1,\nand value 2 is the SAME!\n" ); } else { if ($src1 =~ /^LINK\s+/) { show_link_diff($cnt, $src1, $val1, $val2); } else { prt( "$cnt:1: $src1 = $val1\n" ); prt( "$cnt:2: $src1 = $val2\n" ); } } $done2{$src1} = 1; } else { prt( "$cnt:1: $src1 = $val1\n" ); prt( "$cnt:2: $src1 = NOT AVAILABLE\n" ); } } } foreach $src2 (keys %v6_conf2) { if ( ! defined $done2{$src2} ) { $val2 = $v6_conf2{$src2}; prt( "M2: $src2 = $val2\n" ); } } } return ($added + $subed); # return CHANGE counter } sub is_same_source_file { my ($f1, $f2) = @_; my ($nam1, $dir1, $ext1) = fileparse($f1, qr/\.[^.]*/ ); my ($nam2, $dir2, $ext2) = fileparse($f2, qr/\.[^.]*/ ); # scrunch to all lower case my $lcnm1 = lc($nam1); my $lcex1 = lc($ext1); my $lcnm2 = lc($nam2); my $lcex2 = lc($ext2); if (($lcnm1 eq $lcnm2) && ($lcex1 eq $lcex2)) { return 1; } return 0; } sub is_same_file { my ($f1, $f2) = @_; my $len = length($f1); my $len2 = length($f2); if ($len != $len2) { ###prt( "NOT SAME LENGTH [$f1]($len) vs [$f2]($len2)\n" ); return 0; # not the SAME } $f1 =~ s/\//\\/g; $f2 =~ s/\//\\/g; my $lcf1 = lc($f1); my $lcf2 = lc($f2); my $i = 0; my $ch1 = ''; my $ch2 = ''; while ($i < $len) { $ch1 = substr($lcf1,$i,1); $ch2 = substr($lcf2,$i,1); if ($ch1 ne $ch2) { ###prt( "FAILED at char ".($i + 1)." $ch1 vs $ch2 [$f1]($len) & [$f2]($len2)\n" ); return 0; } $i++; } return 1; # they ARE the SAME } # extracted from utils.pl sub unix_2_dos { my ($f) = shift; $f =~ s/\//\\/g; return $f; } sub sub_common_folder { my ($f1, $f2) = @_; my $off = 0; my $df1 = lc(unix_2_dos($f1)); my $df2 = lc(unix_2_dos($f2)); while ( substr($df1,$off,1) && substr($df2,$off,1) && ( substr($df1,$off,1) eq substr($df2,$off,1) ) ) { $off++; } return substr($f1,$off); } sub set_dbg_show_sources { $dbg_ds1 = 1; $dbg_ds2 = 1; $dbg_ds3 = 1; } sub prtw() { my ($txt) = shift; prt($txt); $txt =~ s/\n$//; push(@warnings,$txt); } sub show_warnings() { if (@warnings) { prt( "\nGot ".scalar @warnings." WARNINGS ...\n" ); foreach my $line (@warnings) { prt("$line\n" ); } } else { prt("\nNo warnings issued.\n"); } #my $s = get_dbg_str(); #prt( "WARNING: DEBUG ON [$s]\n" ) if length($s); prt("\n"); } ############################################################ ###### MAIN ##### if (open INF1, "<$in_file1") { @lines1 = <INF1>; close INF1; $lncnt1 = scalar @lines1; } if (open INF2, "<$in_file2") { @lines2 = <INF2>; close INF2; $lncnt2 = scalar @lines2; } if ($lncnt1 && $lncnt2) { prt( "Comparing $lncnt1, from [$in_file1], with $lncnt2, from [$in_file2]...\n" ); } ### set_dbg_show_sources(); # load FILE 1 clear_load(); process_DSP( $projname, $in_file1 ); @v6_srcs1 = @v6_srcs; # relnm full group filter %v6_defs1 = %v6_defs; %v6_conf1 = %v6_conf; # load FILE 2 clear_load(); process_DSP( $projname, $in_file2 ); @v6_srcs2 = @v6_srcs; # relnm full group filter %v6_defs2 = %v6_defs; %v6_conf2 = %v6_conf; # compare SOURCES compare_dsp_with_dsp($in_file1, $in_file2); prt("\n"); if (@discarded_dupes) { prt("WARNING: discarded ".scalar @discarded_dupes." dupes...\n" ); prt( join(" ",@discarded_dupes)."\n" ); } show_warnings(); close_log($outfile,1); exit(0); ############################################################ # eof - cmp2dsps.pl