mirror of
https://github.com/freebsd/freebsd-src.git
synced 2026-10-28 19:34:43 +01:00
Compare commits
1
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
49bb443250 |
No files matched your search
@@ -1,97 +0,0 @@
|
||||
#!/usr/bin/perl
|
||||
|
||||
# The version of the remote shell program on some Linuxes, at least,
|
||||
# misuses GNU getopt in such a way that it plucks arguments to rsh
|
||||
# that look like command-line switches from anywhere in rsh's
|
||||
# arguments. This is the Wrong Thing to do, and causes older versions
|
||||
# of CCVS to break.
|
||||
|
||||
# In addition, if we live behind a firewall and have to construct a
|
||||
# "pipeline" of rshes through different machines in order to get to
|
||||
# the outside world, each rshd along the way undoes the hard work CCVS
|
||||
# does to put the command to be executed at the far end into a single
|
||||
# argument. Sigh.
|
||||
|
||||
# This script is a very minimal wrapper to rsh which makes sure that
|
||||
# the commands to be executed remotely are packed into a single
|
||||
# argument before we call exec(). It works on the idea of a "proxy
|
||||
# chain", which is a set of machines you go through to get to the CCVS
|
||||
# server machine.
|
||||
|
||||
# Each host you go through before you reach the CCVS server machine
|
||||
# should have a copy of this script somewhere (preferably accessible
|
||||
# directly from your PATH envariable). In addition, each host you go
|
||||
# through before you reach the firewall should have the CVS_PROXY_HOST
|
||||
# envariable set to the next machine in the chain, and CVS_PROXY_USER
|
||||
# set if necessary.
|
||||
|
||||
# This really isn't as complex as it sounds. Honest.
|
||||
|
||||
# Bryan O'Sullivan <[email protected]> April 1995
|
||||
|
||||
$usage = "usage: ccvs-rsh hostname [-l username] command [...]\n";
|
||||
|
||||
if ($#ARGV < 1) {
|
||||
print STDERR $usage;
|
||||
exit 1;
|
||||
}
|
||||
|
||||
# Try to pick a sane version of the remote shell command to run. This
|
||||
# only understands BSD and Linux machines; if your remote shell is
|
||||
# called "remsh" under some System V (e.g. HP-SUX), you should edit
|
||||
# the line manually to suit yourself.
|
||||
|
||||
$rsh = (-x "/usr/ucb/rsh") ? "/usr/ucb/rsh" : "/usr/bin/rsh";
|
||||
|
||||
# If you are not rshing directly to the CCVS server machine, make the
|
||||
# following variable point at ccvs-rsh on the next machine in the
|
||||
# proxy chain. If it's accessible through the PATH envariable, you
|
||||
# can just set this to "ccvs-rsh".
|
||||
|
||||
$ccvs_rsh = "ccvs-rsh";
|
||||
|
||||
# There shouldn't be any user-serviceable parts beyond this point.
|
||||
|
||||
$host = $ARGV[0];
|
||||
|
||||
if ($ARGV[1] eq "-l") {
|
||||
if ($#ARGV < 3) {
|
||||
print STDERR $usage;
|
||||
exit 1;
|
||||
}
|
||||
$user = $ARGV[2];
|
||||
$cbase = 3;
|
||||
} else {
|
||||
$cbase = 1;
|
||||
}
|
||||
|
||||
# You might think you shoul be able to do something like
|
||||
# $command = join(' ', $ARGV[$cbase..$#ARGV]);
|
||||
# to achieve the effect of the following block of code, but it doesn't
|
||||
# work under Perl 4 on Linux, at least. Sigh.
|
||||
|
||||
$command = $ARGV[$cbase];
|
||||
for ($cbase++; $cbase <= $#ARGV; $cbase++) {
|
||||
$command .= " " . $ARGV[$cbase];
|
||||
}
|
||||
|
||||
if (defined $ENV{"CVS_PROXY_HOST"}) {
|
||||
$command = (defined $user)
|
||||
? "$ccvs_rsh $host -l $user $command"
|
||||
: "$ccvs_rsh $host $command";
|
||||
|
||||
if (defined $ENV{"CVS_PROXY_USER"}) {
|
||||
exec ($rsh, $ENV{"CVS_PROXY_HOST"}, "-l", $ENV{"CVS_PROXY_USER"},
|
||||
$command);
|
||||
} else {
|
||||
exec ($rsh, $ENV{"CVS_PROXY_HOST"}, $command);
|
||||
}
|
||||
} elsif (defined $user) {
|
||||
exec ($rsh, $host, "-l", $user, $command);
|
||||
} else {
|
||||
if (defined $ENV{"CVS_PROXY_USER"}) {
|
||||
exec ($rsh, $host, "-l", $ENV{"CVS_PROXY_USER"}, $command);
|
||||
} else {
|
||||
exec ($rsh, $host, $command);
|
||||
}
|
||||
}
|
||||
@@ -1,439 +0,0 @@
|
||||
#! /opt/bin/perl5
|
||||
#
|
||||
# Beware of the fact that this script was not written to handle
|
||||
# branches in the PVCS archives, but it might work nontheless. I have
|
||||
# a specific addition in this latest version that would not be
|
||||
# globally useful: automatically making Framemaker files binary with
|
||||
# -kb (regardless of the file extension).
|
||||
# ---------------------------------
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
|
||||
###########################################################################
|
||||
# FUNCTION:
|
||||
# To recursively walk through a PVCS archive directory tree (archives
|
||||
# located in VCS/ or vcs/ subdirectories) and convert them to RCS archives.
|
||||
# The RCS archive name is the PVCS workfile name with ",v" appended.
|
||||
#
|
||||
# SYNTAX:
|
||||
# The calling syntax is:
|
||||
# pvcs_to_rcs [-l]
|
||||
#
|
||||
# where -l indicates the operation is to be performed only in the current
|
||||
# directory (no recursion)
|
||||
#
|
||||
# EXAMPLE:
|
||||
# pvcs_to_rcs
|
||||
#
|
||||
# Would walk through every VCS or vcs subdir starting at the current directory,
|
||||
# and produce corresponding RCS archives one level above the VCS or vcs subdir.
|
||||
#
|
||||
# NOTES:
|
||||
# * This script does not perform any error checking or logging of any kind
|
||||
# (i.e. USE AT YOUR OWN RISK)
|
||||
# * This script was developed using perl-5.003 on a Sun Solaris 2.5 machine
|
||||
# and executed from a csh
|
||||
# * PVCS archives in VCS/ or vcs/ subdirectories are left intact
|
||||
# * RCS archives are processed in the VCS/ or vcs/ subdirectories and
|
||||
# are moved (forcibly) up one level upon completion of the conversion
|
||||
# * This script has *not* been tested with PVCS archives with branches,
|
||||
# although the only thing I believe that might need to be changed
|
||||
# is the ORDER of revision processing (e.g. you can't checkin 1.2.4.1 if
|
||||
# you haven't yet checked in 1.2).
|
||||
# * All revisions are saved with correct "metadata" (i.e. check-in date,
|
||||
# author, and log message). Any blank log message is replaced with
|
||||
# "no comment". This is because RCS does not allow non-interactive
|
||||
# checkin of a new revision without a comment string.
|
||||
# * Revision numbers are incremented by 1 during the conversion (since
|
||||
# RCS does not allow revision 1.0).
|
||||
# * Version labels are assigned to the appropriate (incremented) revision
|
||||
# numbers. PVCS allows spaces and periods in version labels while RCS
|
||||
# does not. A global search and replace converts " " and "." to "_"
|
||||
# There may be other cases that ought to be added.
|
||||
# * Any workfile within the VCS/ or vcs/ will be deleted (or overwritten)
|
||||
# since it is used in the checkout of each revision
|
||||
# * Locks on PVCS archives should be removed (or the workfiles should be
|
||||
# checked-in) prior to conversion, although the script will blaze through
|
||||
# the archive nonetheless (But you would lose any checked out revision(s))
|
||||
# * The -kb option is added to the RCS archive for workfiles with the following
|
||||
# extensions: .bin .out .btl .rom .a07 .lib .exe .tco .obj .t8u .c8u .o .lku
|
||||
#########################################################################
|
||||
|
||||
require("getcwd.pl");
|
||||
|
||||
#NOTE: Each possible binary extension is delimited by '.'
|
||||
$bin_ext =
|
||||
".bin.out.btl.rom.a07.lib.exe.tco.obj.t8u.c8u.o.lku.BIN.OUT.BTL.ROM.A07.LIB.EXE.TCO.OBJ
|
||||
.T8U.C8U.O.LKU.";
|
||||
|
||||
# the main procedure that is run once in each directory
|
||||
sub execdir
|
||||
{
|
||||
$curlevel= $curlevel +1;
|
||||
|
||||
#local sets the variables directory and prev directory local to the procedure
|
||||
|
||||
local($dir,$prevdir)=@_;
|
||||
|
||||
#change into the directory to be processed
|
||||
|
||||
chdir($dir);
|
||||
|
||||
#open the current directory for listing
|
||||
|
||||
opendir(CURDIR,".");
|
||||
|
||||
#initialize the list of filenames
|
||||
|
||||
local(@filenames);
|
||||
|
||||
#set filenames equal to directory listing
|
||||
|
||||
@filenames = readdir(CURDIR);
|
||||
|
||||
#clean up by closing the directory
|
||||
|
||||
closedir(CURDIR);
|
||||
|
||||
#initialize a list for any subdirectories
|
||||
local(@subdirs);
|
||||
|
||||
#begin a for loop to execute on each filename in the list @filename
|
||||
for (@filenames)
|
||||
|
||||
{
|
||||
#if the file is a directory...
|
||||
if (-d $_)
|
||||
{
|
||||
#include it in @subdir
|
||||
push(@subdirs,$_);
|
||||
}
|
||||
}
|
||||
|
||||
#for loop of subdirs
|
||||
for (@subdirs)
|
||||
#if not a parent directory, run execdir on each sub dir
|
||||
{
|
||||
if (($_ ne '.') and ($_ ne '..') and ($maxlevel > $curlevel))
|
||||
{
|
||||
&execdir($_,$dir);
|
||||
}
|
||||
}
|
||||
|
||||
#save the current directory
|
||||
$cd = &getcwd;
|
||||
|
||||
#Print output header for each directory
|
||||
print("Directory: $cd\n");
|
||||
|
||||
#determine the last directory in this path (to only process vcs or VCS)
|
||||
$_ = $cd;
|
||||
$num_dirs = split /\//;
|
||||
@dirs = @_;
|
||||
$last_dir = $dirs[$num_dirs-1];
|
||||
# print"Last directory is $last_dir\n";
|
||||
|
||||
#shell redirection: output from command in @ARGV is put in $output
|
||||
# $output = `@ARGV`;
|
||||
#begin a for loop to execute on each filename in the list @filename
|
||||
for (@filenames)
|
||||
{
|
||||
if ( (-f $_) and ($_ ne '.') and ($_ ne '..') and ($maxlevel > $curlevel)
|
||||
and ( ( $last_dir eq 'vcs' ) or ( $last_dir eq 'VCS' ) ) )
|
||||
{
|
||||
$got_archivefile = 0;
|
||||
$got_workfile = 0;
|
||||
$got_version_labels = 0;
|
||||
$got_description = 0;
|
||||
$got_rev_count = 0;
|
||||
|
||||
$file = $_;
|
||||
$abs_file = $cd . "/" . $file;
|
||||
print("Converting $abs_file...\n");
|
||||
$vlog_output = `vlog $_`;
|
||||
$_ = $vlog_output;
|
||||
# Split the cvs status output into individual lines
|
||||
@vlog_strings = split /\n/;
|
||||
$num_vlog_strings = @vlog_strings;
|
||||
$_ = $vlog_string[0];
|
||||
if ( /^vlog: warning/ )
|
||||
{
|
||||
print("$abs_file is NOT a valid PVCS archive!!!\n");
|
||||
}
|
||||
elsif( $vlog_output )
|
||||
{
|
||||
|
||||
# Collect all vlog output into appropriate variables
|
||||
|
||||
$num = 0;
|
||||
while( $num < $num_vlog_strings )
|
||||
{
|
||||
# print("$vlog_strings[$num]\n");
|
||||
|
||||
$_ = $vlog_strings[$num];
|
||||
|
||||
if( ( /^Workfile:\s*/ ) && (!$got_workfile ) )
|
||||
{
|
||||
$got_workfile = 1;
|
||||
# get the string to the right of the above search (with any path stripped)
|
||||
$workfile = $';
|
||||
$_=$workfile;
|
||||
$num_fields = split /\//;
|
||||
if ( $num_fields > 1 )
|
||||
{
|
||||
$workfile = $_[$num_fields - 1 ];
|
||||
}
|
||||
# print"Workfile is $workfile\n";
|
||||
}
|
||||
|
||||
elsif( ( /^Archive:\s*/ ) && (!$got_archivefile ) )
|
||||
{
|
||||
$got_archivefile = 1;
|
||||
# get the string to the right of the above search (with any path stripped)
|
||||
$archivefile = $';
|
||||
$_=$archivefile;
|
||||
$num_fields = split /\//;
|
||||
if ( $num_fields > 1 )
|
||||
{
|
||||
$archivefile = $_[$num_fields - 1 ];
|
||||
}
|
||||
# print"Archive is $archivefile\n";
|
||||
}
|
||||
|
||||
elsif ( ( /^Rev count:\s*/ ) && (!$got_rev_count ) )
|
||||
{
|
||||
$got_rev_count = 1;
|
||||
# get the string to the right of the above search
|
||||
$rev_count = $';
|
||||
print"Revision count is $rev_count\n";
|
||||
}
|
||||
|
||||
elsif ( ( /^Version labels:\s*/ ) && (!$got_version_labels ) )
|
||||
{
|
||||
$got_version_labels = 1;
|
||||
$first_vl = $num+1;
|
||||
}
|
||||
|
||||
elsif ( ( /^Description:\s*/ ) && (!$got_description ) )
|
||||
{
|
||||
$got_description = 1;
|
||||
$description = "\"" . $vlog_strings[$num+1] . "\"";
|
||||
# print"Description is $description\n";
|
||||
$last_vl = $num - 1;
|
||||
}
|
||||
|
||||
elsif ( /^Rev\s*/ ) # get all the revision information at once
|
||||
{
|
||||
$rev_index = 0;
|
||||
while ( $rev_index < $rev_count )
|
||||
{
|
||||
$_=$vlog_strings[$num];
|
||||
/^Rev\s*/;
|
||||
$rev_num[$rev_index] = $';
|
||||
$_=$vlog_strings[$num+1];
|
||||
if ( /^Locked\s*/ )
|
||||
{
|
||||
$num += 1;
|
||||
}
|
||||
$_=$vlog_strings[$num+1];
|
||||
/^Checked in:\s*/;
|
||||
$checked_in[$rev_index] = "\"" . $' . "\"";
|
||||
$_=$vlog_strings[$num+3];
|
||||
/^Author id:\s*/;
|
||||
split;
|
||||
$author[$rev_index] = "\"" . $_[2] . "\"";
|
||||
$relative_comment_index = 0;
|
||||
$comment_string = "";
|
||||
while( ( $vlog_strings[$num+4+$relative_comment_index] ne
|
||||
"-----------------------------------" ) &&
|
||||
( $vlog_strings[$num+4+$relative_comment_index] ne
|
||||
"===================================" ) )
|
||||
{
|
||||
# We need the \n added for multi-line comments. There is no effect for
|
||||
# single-line comments since RCS inserts the \n if it doesn't exist already
|
||||
$comment_string = $comment_string .
|
||||
$vlog_strings[$num+4+$relative_comment_index] . "\n";
|
||||
$relative_comment_index += 1;
|
||||
}
|
||||
# Convert any double quotes to an escaped double quote
|
||||
$comment_string =~ s/\"/\\\"/g;
|
||||
$comment[$rev_index] = "\"" . $comment_string . "\"";
|
||||
$num += ( 5 + $relative_comment_index );
|
||||
$rev_index += 1;
|
||||
}
|
||||
$num -= 1; #although there should be nothing left for this to matter
|
||||
}
|
||||
|
||||
$num += 1;
|
||||
|
||||
}
|
||||
|
||||
# Loop through each version label, checking for need to relabel ' ' with '_'.
|
||||
$num_version_labels = $last_vl - $first_vl + 1;
|
||||
print"Version label count is $num_version_labels\n";
|
||||
for( $i = $first_vl; $i <= $last_vl; $i += 1 )
|
||||
{
|
||||
# print("$vlog_strings[$i]\n");
|
||||
$label_index = $i - $first_vl;
|
||||
$_=$vlog_strings[$i];
|
||||
split /\"/;
|
||||
$label = @_[1];
|
||||
$_=@_[2];
|
||||
split;
|
||||
$label_revision[$label_index] = @_[1];
|
||||
|
||||
# Create RCS revision numbers corresponding to PVCS version numbers by
|
||||
# adding 1 to the revision number (# after last .)
|
||||
$rcs_rev = &pvcs_to_rcs_rev_number( $label_revision[$label_index]);
|
||||
$label_revision[ $label_index ] = $rcs_rev;
|
||||
# replace ' ' with '_', if needed
|
||||
$_=$label;
|
||||
$new_label[$label_index] = $label;
|
||||
$new_label[$label_index] =~ s/ /_/g;
|
||||
$new_label[$label_index] =~ s/\./_/g;
|
||||
$new_label[$label_index] = "\"" . $new_label[$label_index] . "\"";
|
||||
# print"Label $new_label[$label_index] is for revision
|
||||
$label_revision[$label_index]\n";
|
||||
}
|
||||
|
||||
# Create RCS revision numbers corresponding to PVCS version numbers by
|
||||
# adding 1 to the revision number (# after last .)
|
||||
|
||||
for( $i = 0; $i < $rev_count; $i += 1 )
|
||||
{
|
||||
$rcs_rev_num[ $i ] = &pvcs_to_rcs_rev_number( $rev_num[ $i ] );
|
||||
# print"PVCS is $rev_num[ $i ]; RCS is $rcs_rev_num[ $i ]\n"
|
||||
}
|
||||
|
||||
# Create RCS archive and check in all revisions, then label.
|
||||
# PVCS vlog lists revisions last-revision-first; reverse that ordering
|
||||
$first_time = 1;
|
||||
|
||||
for( $i = $rev_count - 1; $i >= 0; $i -= 1 )
|
||||
{
|
||||
print "get -r$rev_num[$i] $archivefile\\($workfile\\)\n";
|
||||
# $vcs_output = `vcs -u -r$rev_num[$i] $file`;
|
||||
$get_output = `get -r$rev_num[$i] $archivefile\\($workfile\\)`;
|
||||
if( $first_time )
|
||||
{
|
||||
$first_time = 0;
|
||||
$file_output = `file $workfile`;
|
||||
# If an empty comment is specified, RCS will not check in the file;
|
||||
# check for this case. (but an empty -t- description is fine - go figure!)
|
||||
# Since RCS will pause and ask for a comment if one is not given,
|
||||
# substitute a dummy comment "no comment".
|
||||
if ( $comment[$i] eq "\"\"" )
|
||||
{
|
||||
$ci_command = "ci -f -r$rcs_rev_num[$i] -d$checked_in[$i] -w$author[$i]
|
||||
-t-$description -m\"no comment\" $workfile";
|
||||
}
|
||||
else
|
||||
{
|
||||
$ci_command = "ci -f -r$rcs_rev_num[$i] -d$checked_in[$i] -w$author[$i]
|
||||
-t-$description -m$comment[$i] $workfile";
|
||||
}
|
||||
print "$ci_command\n";
|
||||
$ci_output = `$ci_command`;
|
||||
|
||||
# Also check here whether this file ought to be "binary"
|
||||
$_=$file_output;
|
||||
split;
|
||||
if( $_[1] eq "Frame" )
|
||||
{
|
||||
print"Binary attribute -kb added (file type is Frame)\n";
|
||||
$rcs_output = `rcs -kb $workfile,v`;
|
||||
}
|
||||
else
|
||||
{
|
||||
$_=$workfile;
|
||||
$num_fields = split /\./;
|
||||
if ( $num_fields > 1 )
|
||||
{
|
||||
$ext = "." . $_[$num_fields - 1] . ".";
|
||||
if ( ( index $bin_ext, $ext ) > - 1 )
|
||||
{
|
||||
print"Binary attribute -kb added (file type is $ext)\n";
|
||||
$rcs_output = `rcs -kb $workfile,v`;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
$rcs_output = `rcs -l $workfile`;
|
||||
# If an empty comment is specified, RCS will not check in the file;
|
||||
# check for this case. (but an empty -t- description is fine - go figure!)
|
||||
if ( $comment[$i] eq "\"\"" )
|
||||
{
|
||||
$ci_command = "ci -f -r$rcs_rev_num[$i] -d$checked_in[$i] -w$author[$i]
|
||||
-m\"no comment\" $workfile";
|
||||
}
|
||||
else
|
||||
{
|
||||
$ci_command = "ci -f -r$rcs_rev_num[$i] -d$checked_in[$i] -w$author[$i]
|
||||
-m$comment[$i] $workfile";
|
||||
}
|
||||
print "$ci_command\n";
|
||||
$ci_output = `$ci_command`;
|
||||
}
|
||||
}
|
||||
# Attach version labels
|
||||
for( $i = $num_version_labels - 1; $i >= 0; $i -= 1 )
|
||||
{
|
||||
# print "rcs -n$new_label[$i]:$label_revision[$i] $workfile\n";
|
||||
$rcs_output = `rcs -n$new_label[$i]:$label_revision[$i] $workfile`;
|
||||
print "Version label $new_label[$i] added to revision $label_revision[$i]\n";
|
||||
}
|
||||
|
||||
# Move archive file up one directory level (above vcs/ or VCS/)
|
||||
$mv_output = `mv -f $workfile",v" ..`;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#print the output to STDOUT
|
||||
# print("$output");
|
||||
|
||||
$curlevel=$curlevel - 1;
|
||||
if ($dir ne $prevdir)
|
||||
{
|
||||
chdir('..');
|
||||
}
|
||||
}
|
||||
|
||||
sub pvcs_to_rcs_rev_number
|
||||
{
|
||||
local($input, $num_fields, @rev_string, $return_rev_num, $i);
|
||||
|
||||
$input = @_[0];
|
||||
$_ = $input;
|
||||
$num_fields = split /\./;
|
||||
@rev_string = @_;
|
||||
@rev_string[$num_fields-1] += 1;
|
||||
$return_rev_num = @rev_string[ 0 ];
|
||||
for( $i = 1; $i < $num_fields; $i += 1 )
|
||||
{
|
||||
$return_rev_num = $return_rev_num . "." . @rev_string[ $i ];
|
||||
}
|
||||
return $return_rev_num;
|
||||
}
|
||||
|
||||
##MAIN program: checks to see if there are command line parameters
|
||||
if ($#ARGV > 2) {
|
||||
|
||||
#if not then end and print help message
|
||||
die "Usage: pvcsns [-l]\n"};
|
||||
$curlevel=0-1;$maxlevel=10000;
|
||||
|
||||
if (@ARGV[0] eq "-l") {$maxlevel=1;shift @ARGV;}
|
||||
|
||||
#start the whole thing
|
||||
&execdir(".",".");
|
||||
|
||||
@@ -1,202 +0,0 @@
|
||||
Fri Jan 16 14:58:19 1998 Larry Jones <[email protected]>
|
||||
|
||||
* diff.c, diff3.c: Plug memory leaks.
|
||||
|
||||
Thu Jan 15 13:36:46 1998 Jim Kingdon <[email protected]>
|
||||
|
||||
* Makefile.in (installdirs): New rule, for when ../Makefile
|
||||
recurses into this directory (bug reported by W. L. Estes).
|
||||
|
||||
Tue Nov 11 10:48:19 1997 Jim Kingdon <[email protected]>
|
||||
|
||||
* diff.c (diff_run): Change #ifdef on HAVE_SETMODE to #if to match
|
||||
the other uses (fixes compilation error on unix).
|
||||
|
||||
* diff.c (diff_run): Don't set stdout to binary mode.
|
||||
|
||||
Mon, 10 Nov 1997 Jim Kingdon
|
||||
|
||||
* diff.c (run_diff): Open outfile in binary mode if --binary.
|
||||
|
||||
Thu Nov 6 12:42:12 1997 Karl Fogel <[email protected]>
|
||||
and Paul Eggert <[email protected]>
|
||||
|
||||
* analyze.c: applied Paul Eggert's patch to fix the diff3 merge
|
||||
bug described in ccvs/doc/DIFFUTILS-2.7-BUG:
|
||||
(shift_boundaries): new var `inhibit_hunk_merge'; use it to
|
||||
control something important that I don't quite understand, but
|
||||
Paul apparently does, so that's okay.
|
||||
|
||||
Sat Nov 1 14:17:57 1997 Michael L.H. Brouwer <[email protected]>
|
||||
|
||||
* Makefile.in: Add call to ranlib to build a table of contents for
|
||||
the library since some systems seem to require this.
|
||||
|
||||
1997-10-28 Jim Kingdon
|
||||
|
||||
* .cvsignore: Add files du jour for Visual C++, vc50.pdb and vc50.idb.
|
||||
|
||||
* system.h: Define HAVE_TIME_H.
|
||||
* dir.c [_WIN32]: Define CLOSEDIR_VOID.
|
||||
|
||||
1997-10-18 Jim Kingdon
|
||||
|
||||
* build_diff.com: Add diff3.c
|
||||
|
||||
Fri Sep 26 14:24:42 1997 Tim Pierce <[email protected]>
|
||||
|
||||
* diff.c (diff_run): Save old value of optind before calling
|
||||
getopt_long, then restore before returning. Eventually it would
|
||||
be nice if diff_run were fully reentrant.
|
||||
|
||||
New diff3 library for CVS.
|
||||
* Makefile.in (SOURCES): Add diff3.c.
|
||||
(OBJECTS): Add diff3.o.
|
||||
* diff3.c: New file, copied from diffutils-2.7. See diffutils for
|
||||
earlier ChangeLogs. Undefine initialize_main macro. Remove <signal.h>.
|
||||
(diff3_run): Renamed from main(). Add `outfile' argument. Remove
|
||||
SIGCLD handling; we do not fork. Save optind and reset to 0
|
||||
before calling getopt_long; restore after option processing done.
|
||||
(read_diff): Use diff_run with a temporary output file,
|
||||
instead of forking a diff subprocess and reading from a pipe.
|
||||
Change DIFF_PROGRAM to "diff"; this argument is now used only for
|
||||
diagnostic reporting.
|
||||
(xmalloc, xrealloc): Removed.
|
||||
(diff_program): Removed.
|
||||
(diff_program_name): Made extern, so it may be used in other
|
||||
library calls like `error'.
|
||||
(initialize_main): New function.
|
||||
|
||||
Namespace munging. util.c defines both fatal() and
|
||||
perror_with_exit(), but these cannot be used to abort diff3: both
|
||||
attempt to longjmp() to a buffer set in diff.c, used only by
|
||||
diff_run. This is an awful solution, but necessary until the code
|
||||
can be cleaned up. (These functions do not *have* to be renamed,
|
||||
since both are declared static to diff3.c and should not clash
|
||||
with libdiff.a, but it reduces potential confusion.)
|
||||
* diff3.c (diff3_fatal): Renamed from fatal.
|
||||
(diff3_perror_with_exit): Renamed from perror_with_exit.
|
||||
|
||||
Eliminate exit calls.
|
||||
(try_help): Change from `void' to `int'. Return, do not exit.
|
||||
(diff3_fatal, diff3_perror_with_exit, process_diff): Change `exit'
|
||||
to DIFF3_ABORT.
|
||||
(diff3_run): Initialize jump buffer for nonlocal exits. Change
|
||||
exit calls to returns. Change `perror_with_exit' to
|
||||
`perror_with_name' and add a return. Change `fatal' to
|
||||
`diff_error' and add a return. The reasoning is that we shouldn't
|
||||
rely on setjmp/longjmp any more than necessary.
|
||||
|
||||
Redirect stdout.
|
||||
(check_output): Renamed from check_stdout. Take stream argument
|
||||
instead of blindly checking stdout. Do not close stream, but
|
||||
merely fflush it.
|
||||
(diff3_run): Initialize outstream, and close when done. Pass this
|
||||
stream (instead of stdout) to output_diff3_edscript,
|
||||
output_diff3_merge, and output_diff3.
|
||||
|
||||
Thu Sep 25 14:34:22 1997 Jim Kingdon <[email protected]>
|
||||
|
||||
* util.c (begin_output, finish_output): If PR_PROGRAM is not
|
||||
defined (VMS), just give a fatal error if --paginate specified.
|
||||
|
||||
* Makefile.in (DISTFILES): Add ChangeLog build_diff.com
|
||||
Makefile.in.
|
||||
* build_diff.com: New file.
|
||||
|
||||
Wed Sep 24 10:27:00 1997 Jim Kingdon <[email protected]>
|
||||
|
||||
* Makefile.in: Also set top_srcdir. Needed to make today's other
|
||||
Makefile.in change work.
|
||||
|
||||
* .cvsignore: New file.
|
||||
|
||||
* Makefile.in (COMPILE): Add -I options for srcdir (perhaps
|
||||
unneeded) and change -I option for lib to use top_srcdir (needed
|
||||
to avoid mixups with CVS's regex.h vs. the system one).
|
||||
|
||||
Sun Sep 21 19:44:42 1997 Jim Kingdon <[email protected]>
|
||||
|
||||
* Makefile.in (util.o): Change util.c to $<, needed for srcdir.
|
||||
|
||||
Sat Sep 20 12:06:41 1997 Tim Pierce <[email protected]>
|
||||
|
||||
New diff library for CVS, based on diffutils-2.7. See diffutils
|
||||
for earlier ChangeLogs.
|
||||
* Makefile.in, analyze.c, cmpbuf.c, cmpbuf.h, config.hin,
|
||||
context.c, diagmeet.note, diff.c, diff.h, dir.c, ed.c, ifdef.c,
|
||||
io.c, normal.c, side.c, stamp-h.in, system.h, util.c, version.c:
|
||||
New files.
|
||||
(COMPILE): Add -I../lib, so we can get getopt.h.
|
||||
|
||||
* Makefile.in: Removed anything not related to libdiff.a.
|
||||
(dist-dir): New target, copied from ../lib/Makefile.in.
|
||||
(DISTFILES): New variable.
|
||||
(SOURCES): Renamed from `srcs'.
|
||||
(OBJECTS): Renamed from `libdiff_o'.
|
||||
(Makefile): Changed dependencies to reflect
|
||||
new, shallow config directory structure.
|
||||
(stamp-h.in, config.h.in, config.h, stamp-h): Removed.
|
||||
* stamp-h.in, config.h.in: Removed.
|
||||
|
||||
* system.h: Remove dup2 macro (provided by ../lib/dup2.c).
|
||||
Include stdlib.h if STDC_HEADERS is defined (not just
|
||||
HAVE_STDLIB_H).
|
||||
|
||||
Sat Sep 20 05:32:18 1997 Tim Pierce <[email protected]>
|
||||
|
||||
Diff librarification.
|
||||
|
||||
* diff.c (diff_run): New function, renamed from `main'.
|
||||
Initialize `outfile' based on the value of the new `out' filename
|
||||
argument.
|
||||
(initialize_main): New function.
|
||||
* system.h: Removed initialize_main macro.
|
||||
* diffmain.c: New file.
|
||||
* Makefile.in (diff): Added diffmain.o.
|
||||
(libdiff): New target.
|
||||
(AR, libdiff_o): New variables. libdiff_o does not include
|
||||
xmalloc.o, fnmatch.o, getopt.o, getopt1.o, regex.o or error.o,
|
||||
because these functions are already present in CVS. It will take
|
||||
some work to make this more general-purpose.
|
||||
|
||||
Redirect standard output.
|
||||
* util.c: Redirect stdout to outfile: change all naked `printf'
|
||||
and `putchar' statements to `fprintf (outfile)' and `putc (...,
|
||||
outfile)' throughout. This should permit redirecting diff output
|
||||
by changing `outfile' just once in `diff_run'.
|
||||
(output_in_progress): New variable.
|
||||
(begin_output, finish_output): Use `output_in_progress', rather than
|
||||
`outfile', as a semaphore to avoid reentrancy problems.
|
||||
(finish_output): Close `outfile' only if paginate_flag is set.
|
||||
* diff.c (check_output): New function, was check_stdout. Take a
|
||||
`file' argument, and flush it instead of closing it.
|
||||
(diff_run): Change check_stdout to check_output.
|
||||
(compare_files): Fflush outfile, not stdout.
|
||||
|
||||
Eliminate exit statements.
|
||||
* diff.h: Include setjmp.h.
|
||||
(diff_abort_buf): New variable.
|
||||
(DIFF_ABORT): New macro.
|
||||
* diff.c (diff_run): Change all `exit' statements to `return'.
|
||||
Set up diff_abort_buf, so we can abort diff without
|
||||
terminating (for libdiff.a).
|
||||
(try_help): Return int instead of void; do not exit.
|
||||
* util.c (fatal): Use DIFF_ABORT instead of exit.
|
||||
(pfatal_with_name): Use DIFF_ABORT instead of exit.
|
||||
|
||||
Namespace cleanup (rudimentary). Strictly speaking, this is not
|
||||
necessary to make diff into a library. However, namespace
|
||||
clashes between diff and CVS must be resolved immediately, since
|
||||
CVS is the first application targeted for use with difflib.
|
||||
|
||||
* analyze.c, diff.c, diff.h, util.c (diff_error): Renamed from `error'.
|
||||
|
||||
* version.c, diff.c, diff.h, cmp.c, diff3.c, sdiff.c
|
||||
(diff_version_string): Renamed from version_string.
|
||||
* diff.c, util.c, diff.h, diff3.c, error.c (diff_program_name):
|
||||
Renamed from program_name.
|
||||
|
||||
* util.c (xmalloc, xrealloc): Removed.
|
||||
* Makefile.in (diff_o): Added error.o and xmalloc.o.
|
||||
|
||||
@@ -1,104 +0,0 @@
|
||||
# Makefile for GNU DIFF
|
||||
# Copyright (C) 1988,1989,1991,1992,1993,1994,1997 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU DIFF.
|
||||
#
|
||||
# GNU DIFF is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU DIFF is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with GNU DIFF; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
|
||||
#### Start of system configuration section. ####
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
subdir = diff
|
||||
|
||||
CC = @CC@
|
||||
AR = ar
|
||||
|
||||
CPPFLAGS = @CPPFLAGS@
|
||||
DEFS = @DEFS@
|
||||
RANLIB = @RANLIB@
|
||||
CFLAGS = @CFLAGS@
|
||||
|
||||
prefix = @prefix@
|
||||
exec_prefix = @exec_prefix@
|
||||
|
||||
PR_PROGRAM = /bin/pr
|
||||
|
||||
#### End of system configuration section. ####
|
||||
|
||||
SHELL = /bin/sh
|
||||
|
||||
# The source files for all of the programs.
|
||||
SOURCES = diff.c diff3.c analyze.c cmpbuf.c cmpbuf.h io.c context.c ed.c \
|
||||
normal.c ifdef.c util.c dir.c version.c diff.h side.c system.h
|
||||
OBJECTS = diff.o diff3.o analyze.o cmpbuf.o dir.o io.o util.o \
|
||||
context.o ed.o ifdef.o normal.o side.o version.o
|
||||
DISTFILES = $(SOURCES) ChangeLog build_diff.com Makefile.in
|
||||
|
||||
all: libdiff.a
|
||||
|
||||
# $(top_srcdir)/lib is so we don't get the system-supplied headers for
|
||||
# functions that we supply ourselves in lib. $(srcdir) is perhaps not
|
||||
# necessary if we assume the unix compiler behavior whereby "" looks
|
||||
# in the directory containing the .c file first.
|
||||
# -I. is probably unnecessary (I don't think we generate any .h files).
|
||||
# -I.. is for config.h.
|
||||
COMPILE = $(CC) -c $(CPPFLAGS) $(DEFS) \
|
||||
-I. -I.. -I$(srcdir) -I$(top_srcdir)/lib $(CFLAGS)
|
||||
|
||||
.c.o:
|
||||
$(COMPILE) $<
|
||||
|
||||
libdiff libdiff.a: $(OBJECTS)
|
||||
$(AR) cr libdiff.a $(OBJECTS)
|
||||
-$(RANLIB) libdiff.a
|
||||
|
||||
$(OBJECTS): diff.h system.h
|
||||
analyze.o cmpbuf.o: cmpbuf.h
|
||||
|
||||
util.o: util.c
|
||||
$(COMPILE) -DPR_PROGRAM=\"$(PR_PROGRAM)\" $<
|
||||
|
||||
install: all
|
||||
|
||||
installdirs:
|
||||
@: nothing to do for installdirs
|
||||
.PHONY: installdirs
|
||||
|
||||
TAGS: $(SOURCES)
|
||||
etags $(SOURCES)
|
||||
|
||||
clean:
|
||||
rm -f *.o *.a core
|
||||
|
||||
mostlyclean: clean
|
||||
|
||||
distclean: clean
|
||||
rm -f TAGS tags Makefile
|
||||
|
||||
realclean: distclean
|
||||
|
||||
Makefile: Makefile.in ../config.status
|
||||
cd .. && CONFIG_FILES=$(subdir)/$@ CONFIG_HEADERS= ./config.status
|
||||
|
||||
dist-dir:
|
||||
mkdir ${DISTDIR}
|
||||
for i in ${DISTFILES}; do \
|
||||
ln $(srcdir)/$${i} ${DISTDIR}; \
|
||||
done
|
||||
|
||||
# Prevent GNU make v3 from overflowing arg limit on SysV.
|
||||
.NOEXPORT:
|
||||
File diff suppressed because it is too large.
Load diff
@@ -1,40 +0,0 @@
|
||||
/* Buffer primitives for comparison operations.
|
||||
Copyright (C) 1993 Free Software Foundation, Inc.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
#include "system.h"
|
||||
#include "cmpbuf.h"
|
||||
|
||||
/* Least common multiple of two buffer sizes A and B. */
|
||||
|
||||
size_t
|
||||
buffer_lcm (a, b)
|
||||
size_t a, b;
|
||||
{
|
||||
size_t m, n, r;
|
||||
|
||||
/* Yield reasonable values if buffer sizes are zero. */
|
||||
if (!a)
|
||||
return b ? b : 8 * 1024;
|
||||
if (!b)
|
||||
return a;
|
||||
|
||||
/* n = gcd (a, b) */
|
||||
for (m = a, n = b; (r = m % n) != 0; m = n, n = r)
|
||||
continue;
|
||||
|
||||
return a/n * b;
|
||||
}
|
||||
@@ -1,20 +0,0 @@
|
||||
/* Buffer primitives for comparison operations.
|
||||
Copyright (C) 1993 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
size_t buffer_lcm PARAMS((size_t, size_t));
|
||||
@@ -1,468 +0,0 @@
|
||||
/* Context-format output routines for GNU DIFF.
|
||||
Copyright (C) 1988,1989,1991,1992,1993,1994 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
static struct change *find_hunk PARAMS((struct change *));
|
||||
static void find_function PARAMS((struct file_data const *, int, char const **, size_t *));
|
||||
static void mark_ignorable PARAMS((struct change *));
|
||||
static void pr_context_hunk PARAMS((struct change *));
|
||||
static void pr_unidiff_hunk PARAMS((struct change *));
|
||||
static void print_context_label PARAMS ((char const *, struct file_data *, char const *));
|
||||
static void print_context_number_range PARAMS((struct file_data const *, int, int));
|
||||
static void print_unidiff_number_range PARAMS((struct file_data const *, int, int));
|
||||
|
||||
/* Last place find_function started searching from. */
|
||||
static int find_function_last_search;
|
||||
|
||||
/* The value find_function returned when it started searching there. */
|
||||
static int find_function_last_match;
|
||||
|
||||
/* Print a label for a context diff, with a file name and date or a label. */
|
||||
|
||||
static void
|
||||
print_context_label (mark, inf, label)
|
||||
char const *mark;
|
||||
struct file_data *inf;
|
||||
char const *label;
|
||||
{
|
||||
if (label)
|
||||
fprintf (outfile, "%s %s\n", mark, label);
|
||||
else
|
||||
{
|
||||
char const *ct = ctime (&inf->stat.st_mtime);
|
||||
if (!ct)
|
||||
ct = "?\n";
|
||||
/* See Posix.2 section 4.17.6.1.4 for this format. */
|
||||
fprintf (outfile, "%s %s\t%s", mark, inf->name, ct);
|
||||
}
|
||||
}
|
||||
|
||||
/* Print a header for a context diff, with the file names and dates. */
|
||||
|
||||
void
|
||||
print_context_header (inf, unidiff_flag)
|
||||
struct file_data inf[];
|
||||
int unidiff_flag;
|
||||
{
|
||||
if (unidiff_flag)
|
||||
{
|
||||
print_context_label ("---", &inf[0], file_label[0]);
|
||||
print_context_label ("+++", &inf[1], file_label[1]);
|
||||
}
|
||||
else
|
||||
{
|
||||
print_context_label ("***", &inf[0], file_label[0]);
|
||||
print_context_label ("---", &inf[1], file_label[1]);
|
||||
}
|
||||
}
|
||||
|
||||
/* Print an edit script in context format. */
|
||||
|
||||
void
|
||||
print_context_script (script, unidiff_flag)
|
||||
struct change *script;
|
||||
int unidiff_flag;
|
||||
{
|
||||
if (ignore_blank_lines_flag || ignore_regexp_list)
|
||||
mark_ignorable (script);
|
||||
else
|
||||
{
|
||||
struct change *e;
|
||||
for (e = script; e; e = e->link)
|
||||
e->ignore = 0;
|
||||
}
|
||||
|
||||
find_function_last_search = - files[0].prefix_lines;
|
||||
find_function_last_match = find_function_last_search - 1;
|
||||
|
||||
if (unidiff_flag)
|
||||
print_script (script, find_hunk, pr_unidiff_hunk);
|
||||
else
|
||||
print_script (script, find_hunk, pr_context_hunk);
|
||||
}
|
||||
|
||||
/* Print a pair of line numbers with a comma, translated for file FILE.
|
||||
If the second number is not greater, use the first in place of it.
|
||||
|
||||
Args A and B are internal line numbers.
|
||||
We print the translated (real) line numbers. */
|
||||
|
||||
static void
|
||||
print_context_number_range (file, a, b)
|
||||
struct file_data const *file;
|
||||
int a, b;
|
||||
{
|
||||
int trans_a, trans_b;
|
||||
translate_range (file, a, b, &trans_a, &trans_b);
|
||||
|
||||
/* Note: we can have B < A in the case of a range of no lines.
|
||||
In this case, we should print the line number before the range,
|
||||
which is B. */
|
||||
if (trans_b > trans_a)
|
||||
fprintf (outfile, "%d,%d", trans_a, trans_b);
|
||||
else
|
||||
fprintf (outfile, "%d", trans_b);
|
||||
}
|
||||
|
||||
/* Print a portion of an edit script in context format.
|
||||
HUNK is the beginning of the portion to be printed.
|
||||
The end is marked by a `link' that has been nulled out.
|
||||
|
||||
Prints out lines from both files, and precedes each
|
||||
line with the appropriate flag-character. */
|
||||
|
||||
static void
|
||||
pr_context_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int first0, last0, first1, last1, show_from, show_to, i;
|
||||
struct change *next;
|
||||
char const *prefix;
|
||||
char const *function;
|
||||
size_t function_length;
|
||||
FILE *out;
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
|
||||
analyze_hunk (hunk, &first0, &last0, &first1, &last1, &show_from, &show_to);
|
||||
|
||||
if (!show_from && !show_to)
|
||||
return;
|
||||
|
||||
/* Include a context's width before and after. */
|
||||
|
||||
i = - files[0].prefix_lines;
|
||||
first0 = max (first0 - context, i);
|
||||
first1 = max (first1 - context, i);
|
||||
last0 = min (last0 + context, files[0].valid_lines - 1);
|
||||
last1 = min (last1 + context, files[1].valid_lines - 1);
|
||||
|
||||
/* If desired, find the preceding function definition line in file 0. */
|
||||
function = 0;
|
||||
if (function_regexp_list)
|
||||
find_function (&files[0], first0, &function, &function_length);
|
||||
|
||||
begin_output ();
|
||||
out = outfile;
|
||||
|
||||
/* If we looked for and found a function this is part of,
|
||||
include its name in the header of the diff section. */
|
||||
fprintf (out, "***************");
|
||||
|
||||
if (function)
|
||||
{
|
||||
fprintf (out, " ");
|
||||
fwrite (function, 1, min (function_length - 1, 40), out);
|
||||
}
|
||||
|
||||
fprintf (out, "\n*** ");
|
||||
print_context_number_range (&files[0], first0, last0);
|
||||
fprintf (out, " ****\n");
|
||||
|
||||
if (show_from)
|
||||
{
|
||||
next = hunk;
|
||||
|
||||
for (i = first0; i <= last0; i++)
|
||||
{
|
||||
/* Skip past changes that apply (in file 0)
|
||||
only to lines before line I. */
|
||||
|
||||
while (next && next->line0 + next->deleted <= i)
|
||||
next = next->link;
|
||||
|
||||
/* Compute the marking for line I. */
|
||||
|
||||
prefix = " ";
|
||||
if (next && next->line0 <= i)
|
||||
/* The change NEXT covers this line.
|
||||
If lines were inserted here in file 1, this is "changed".
|
||||
Otherwise it is "deleted". */
|
||||
prefix = (next->inserted > 0 ? "!" : "-");
|
||||
|
||||
print_1_line (prefix, &files[0].linbuf[i]);
|
||||
}
|
||||
}
|
||||
|
||||
fprintf (out, "--- ");
|
||||
print_context_number_range (&files[1], first1, last1);
|
||||
fprintf (out, " ----\n");
|
||||
|
||||
if (show_to)
|
||||
{
|
||||
next = hunk;
|
||||
|
||||
for (i = first1; i <= last1; i++)
|
||||
{
|
||||
/* Skip past changes that apply (in file 1)
|
||||
only to lines before line I. */
|
||||
|
||||
while (next && next->line1 + next->inserted <= i)
|
||||
next = next->link;
|
||||
|
||||
/* Compute the marking for line I. */
|
||||
|
||||
prefix = " ";
|
||||
if (next && next->line1 <= i)
|
||||
/* The change NEXT covers this line.
|
||||
If lines were deleted here in file 0, this is "changed".
|
||||
Otherwise it is "inserted". */
|
||||
prefix = (next->deleted > 0 ? "!" : "+");
|
||||
|
||||
print_1_line (prefix, &files[1].linbuf[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Print a pair of line numbers with a comma, translated for file FILE.
|
||||
If the second number is smaller, use the first in place of it.
|
||||
If the numbers are equal, print just one number.
|
||||
|
||||
Args A and B are internal line numbers.
|
||||
We print the translated (real) line numbers. */
|
||||
|
||||
static void
|
||||
print_unidiff_number_range (file, a, b)
|
||||
struct file_data const *file;
|
||||
int a, b;
|
||||
{
|
||||
int trans_a, trans_b;
|
||||
translate_range (file, a, b, &trans_a, &trans_b);
|
||||
|
||||
/* Note: we can have B < A in the case of a range of no lines.
|
||||
In this case, we should print the line number before the range,
|
||||
which is B. */
|
||||
if (trans_b <= trans_a)
|
||||
fprintf (outfile, trans_b == trans_a ? "%d" : "%d,0", trans_b);
|
||||
else
|
||||
fprintf (outfile, "%d,%d", trans_a, trans_b - trans_a + 1);
|
||||
}
|
||||
|
||||
/* Print a portion of an edit script in unidiff format.
|
||||
HUNK is the beginning of the portion to be printed.
|
||||
The end is marked by a `link' that has been nulled out.
|
||||
|
||||
Prints out lines from both files, and precedes each
|
||||
line with the appropriate flag-character. */
|
||||
|
||||
static void
|
||||
pr_unidiff_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int first0, last0, first1, last1, show_from, show_to, i, j, k;
|
||||
struct change *next;
|
||||
char const *function;
|
||||
size_t function_length;
|
||||
FILE *out;
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
|
||||
analyze_hunk (hunk, &first0, &last0, &first1, &last1, &show_from, &show_to);
|
||||
|
||||
if (!show_from && !show_to)
|
||||
return;
|
||||
|
||||
/* Include a context's width before and after. */
|
||||
|
||||
i = - files[0].prefix_lines;
|
||||
first0 = max (first0 - context, i);
|
||||
first1 = max (first1 - context, i);
|
||||
last0 = min (last0 + context, files[0].valid_lines - 1);
|
||||
last1 = min (last1 + context, files[1].valid_lines - 1);
|
||||
|
||||
/* If desired, find the preceding function definition line in file 0. */
|
||||
function = 0;
|
||||
if (function_regexp_list)
|
||||
find_function (&files[0], first0, &function, &function_length);
|
||||
|
||||
begin_output ();
|
||||
out = outfile;
|
||||
|
||||
fprintf (out, "@@ -");
|
||||
print_unidiff_number_range (&files[0], first0, last0);
|
||||
fprintf (out, " +");
|
||||
print_unidiff_number_range (&files[1], first1, last1);
|
||||
fprintf (out, " @@");
|
||||
|
||||
/* If we looked for and found a function this is part of,
|
||||
include its name in the header of the diff section. */
|
||||
|
||||
if (function)
|
||||
{
|
||||
putc (' ', out);
|
||||
fwrite (function, 1, min (function_length - 1, 40), out);
|
||||
}
|
||||
putc ('\n', out);
|
||||
|
||||
next = hunk;
|
||||
i = first0;
|
||||
j = first1;
|
||||
|
||||
while (i <= last0 || j <= last1)
|
||||
{
|
||||
|
||||
/* If the line isn't a difference, output the context from file 0. */
|
||||
|
||||
if (!next || i < next->line0)
|
||||
{
|
||||
putc (tab_align_flag ? '\t' : ' ', out);
|
||||
print_1_line (0, &files[0].linbuf[i++]);
|
||||
j++;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* For each difference, first output the deleted part. */
|
||||
|
||||
k = next->deleted;
|
||||
while (k--)
|
||||
{
|
||||
putc ('-', out);
|
||||
if (tab_align_flag)
|
||||
putc ('\t', out);
|
||||
print_1_line (0, &files[0].linbuf[i++]);
|
||||
}
|
||||
|
||||
/* Then output the inserted part. */
|
||||
|
||||
k = next->inserted;
|
||||
while (k--)
|
||||
{
|
||||
putc ('+', out);
|
||||
if (tab_align_flag)
|
||||
putc ('\t', out);
|
||||
print_1_line (0, &files[1].linbuf[j++]);
|
||||
}
|
||||
|
||||
/* We're done with this hunk, so on to the next! */
|
||||
|
||||
next = next->link;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Scan a (forward-ordered) edit script for the first place that more than
|
||||
2*CONTEXT unchanged lines appear, and return a pointer
|
||||
to the `struct change' for the last change before those lines. */
|
||||
|
||||
static struct change *
|
||||
find_hunk (start)
|
||||
struct change *start;
|
||||
{
|
||||
struct change *prev;
|
||||
int top0, top1;
|
||||
int thresh;
|
||||
|
||||
do
|
||||
{
|
||||
/* Compute number of first line in each file beyond this changed. */
|
||||
top0 = start->line0 + start->deleted;
|
||||
top1 = start->line1 + start->inserted;
|
||||
prev = start;
|
||||
start = start->link;
|
||||
/* Threshold distance is 2*CONTEXT between two non-ignorable changes,
|
||||
but only CONTEXT if one is ignorable. */
|
||||
thresh = ((prev->ignore || (start && start->ignore))
|
||||
? context
|
||||
: 2 * context + 1);
|
||||
/* It is not supposed to matter which file we check in the end-test.
|
||||
If it would matter, crash. */
|
||||
if (start && start->line0 - top0 != start->line1 - top1)
|
||||
abort ();
|
||||
} while (start
|
||||
/* Keep going if less than THRESH lines
|
||||
elapse before the affected line. */
|
||||
&& start->line0 < top0 + thresh);
|
||||
|
||||
return prev;
|
||||
}
|
||||
|
||||
/* Set the `ignore' flag properly in each change in SCRIPT.
|
||||
It should be 1 if all the lines inserted or deleted in that change
|
||||
are ignorable lines. */
|
||||
|
||||
static void
|
||||
mark_ignorable (script)
|
||||
struct change *script;
|
||||
{
|
||||
while (script)
|
||||
{
|
||||
struct change *next = script->link;
|
||||
int first0, last0, first1, last1, deletes, inserts;
|
||||
|
||||
/* Turn this change into a hunk: detach it from the others. */
|
||||
script->link = 0;
|
||||
|
||||
/* Determine whether this change is ignorable. */
|
||||
analyze_hunk (script, &first0, &last0, &first1, &last1, &deletes, &inserts);
|
||||
/* Reconnect the chain as before. */
|
||||
script->link = next;
|
||||
|
||||
/* If the change is ignorable, mark it. */
|
||||
script->ignore = (!deletes && !inserts);
|
||||
|
||||
/* Advance to the following change. */
|
||||
script = next;
|
||||
}
|
||||
}
|
||||
|
||||
/* Find the last function-header line in FILE prior to line number LINENUM.
|
||||
This is a line containing a match for the regexp in `function_regexp'.
|
||||
Store the address of the line text into LINEP and the length of the
|
||||
line into LENP.
|
||||
Do not store anything if no function-header is found. */
|
||||
|
||||
static void
|
||||
find_function (file, linenum, linep, lenp)
|
||||
struct file_data const *file;
|
||||
int linenum;
|
||||
char const **linep;
|
||||
size_t *lenp;
|
||||
{
|
||||
int i = linenum;
|
||||
int last = find_function_last_search;
|
||||
find_function_last_search = i;
|
||||
|
||||
while (--i >= last)
|
||||
{
|
||||
/* See if this line is what we want. */
|
||||
struct regexp_list *r;
|
||||
char const *line = file->linbuf[i];
|
||||
size_t len = file->linbuf[i + 1] - line;
|
||||
|
||||
for (r = function_regexp_list; r; r = r->next)
|
||||
if (0 <= re_search (&r->buf, line, len, 0, len, 0))
|
||||
{
|
||||
*linep = line;
|
||||
*lenp = len;
|
||||
find_function_last_match = i;
|
||||
return;
|
||||
}
|
||||
}
|
||||
/* If we search back to where we started searching the previous time,
|
||||
find the line we found last time. */
|
||||
if (find_function_last_match >= - file->prefix_lines)
|
||||
{
|
||||
i = find_function_last_match;
|
||||
*linep = file->linbuf[i];
|
||||
*lenp = file->linbuf[i + 1] - *linep;
|
||||
return;
|
||||
}
|
||||
return;
|
||||
}
|
||||
@@ -1,71 +0,0 @@
|
||||
Here is a comparison matrix which shows a case in which
|
||||
it is possible for the forward and backward scan in `diag'
|
||||
to meet along a nonzero length of diagonal simultaneous
|
||||
(so that bdiag[d] and fdiag[d] are not equal)
|
||||
even though there is no snake on that diagonal at the meeting point.
|
||||
|
||||
|
||||
85 1 1 1 159 1 1 17
|
||||
1 2 3 4
|
||||
60
|
||||
1 2
|
||||
1
|
||||
2 2 3 4
|
||||
71
|
||||
3 3 4 5
|
||||
85
|
||||
4 3 4 5
|
||||
17
|
||||
5 4 5
|
||||
1
|
||||
6 4 5 6
|
||||
183
|
||||
7 5 6 7
|
||||
10
|
||||
8 6 7
|
||||
1
|
||||
9 6 7 8
|
||||
12
|
||||
7 8 9 10
|
||||
13
|
||||
10 8 9 10
|
||||
14
|
||||
10 9 10
|
||||
17
|
||||
10 10
|
||||
1
|
||||
10 9 10
|
||||
1
|
||||
8 10 10 10
|
||||
183
|
||||
8 7 9 9 9
|
||||
10
|
||||
7 6 8 9 8 8
|
||||
1
|
||||
6 5 7 7
|
||||
1
|
||||
5 6 6
|
||||
1
|
||||
5 5 5
|
||||
50
|
||||
5 4 4 4
|
||||
1
|
||||
4 3 3
|
||||
85
|
||||
5 4 3 2 2
|
||||
1
|
||||
2 1
|
||||
17
|
||||
5 4 3 2 1 1
|
||||
1
|
||||
1 0
|
||||
85 1 1 1 159 1 1 17
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
File diff suppressed because it is too large.
Load diff
@@ -1,345 +0,0 @@
|
||||
/* Shared definitions for GNU DIFF
|
||||
Copyright (C) 1988, 89, 91, 92, 93, 97 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
#include "system.h"
|
||||
#include <stdio.h>
|
||||
#include <setjmp.h>
|
||||
#include "regex.h"
|
||||
|
||||
#define TAB_WIDTH 8
|
||||
|
||||
/* Variables for command line options */
|
||||
|
||||
#ifndef GDIFF_MAIN
|
||||
#define EXTERN extern
|
||||
#else
|
||||
#define EXTERN
|
||||
#endif
|
||||
|
||||
enum output_style {
|
||||
/* Default output style. */
|
||||
OUTPUT_NORMAL,
|
||||
/* Output the differences with lines of context before and after (-c). */
|
||||
OUTPUT_CONTEXT,
|
||||
/* Output the differences in a unified context diff format (-u). */
|
||||
OUTPUT_UNIFIED,
|
||||
/* Output the differences as commands suitable for `ed' (-e). */
|
||||
OUTPUT_ED,
|
||||
/* Output the diff as a forward ed script (-f). */
|
||||
OUTPUT_FORWARD_ED,
|
||||
/* Like -f, but output a count of changed lines in each "command" (-n). */
|
||||
OUTPUT_RCS,
|
||||
/* Output merged #ifdef'd file (-D). */
|
||||
OUTPUT_IFDEF,
|
||||
/* Output sdiff style (-y). */
|
||||
OUTPUT_SDIFF
|
||||
};
|
||||
|
||||
/* True for output styles that are robust,
|
||||
i.e. can handle a file that ends in a non-newline. */
|
||||
#define ROBUST_OUTPUT_STYLE(S) ((S) != OUTPUT_ED && (S) != OUTPUT_FORWARD_ED)
|
||||
|
||||
EXTERN enum output_style output_style;
|
||||
|
||||
/* Nonzero if output cannot be generated for identical files. */
|
||||
EXTERN int no_diff_means_no_output;
|
||||
|
||||
/* Number of lines of context to show in each set of diffs.
|
||||
This is zero when context is not to be shown. */
|
||||
EXTERN int context;
|
||||
|
||||
/* Consider all files as text files (-a).
|
||||
Don't interpret codes over 0177 as implying a "binary file". */
|
||||
EXTERN int always_text_flag;
|
||||
|
||||
/* Number of lines to keep in identical prefix and suffix. */
|
||||
EXTERN int horizon_lines;
|
||||
|
||||
/* Ignore changes in horizontal white space (-b). */
|
||||
EXTERN int ignore_space_change_flag;
|
||||
|
||||
/* Ignore all horizontal white space (-w). */
|
||||
EXTERN int ignore_all_space_flag;
|
||||
|
||||
/* Ignore changes that affect only blank lines (-B). */
|
||||
EXTERN int ignore_blank_lines_flag;
|
||||
|
||||
/* 1 if lines may match even if their contents do not match exactly.
|
||||
This depends on various options. */
|
||||
EXTERN int ignore_some_line_changes;
|
||||
|
||||
/* 1 if files may match even if their contents are not byte-for-byte identical.
|
||||
This depends on various options. */
|
||||
EXTERN int ignore_some_changes;
|
||||
|
||||
/* Ignore differences in case of letters (-i). */
|
||||
EXTERN int ignore_case_flag;
|
||||
|
||||
/* File labels for `-c' output headers (-L). */
|
||||
EXTERN char *file_label[2];
|
||||
|
||||
struct regexp_list
|
||||
{
|
||||
struct re_pattern_buffer buf;
|
||||
struct regexp_list *next;
|
||||
};
|
||||
|
||||
/* Regexp to identify function-header lines (-F). */
|
||||
EXTERN struct regexp_list *function_regexp_list;
|
||||
|
||||
/* Ignore changes that affect only lines matching this regexp (-I). */
|
||||
EXTERN struct regexp_list *ignore_regexp_list;
|
||||
|
||||
/* Say only whether files differ, not how (-q). */
|
||||
EXTERN int no_details_flag;
|
||||
|
||||
/* Report files compared that match (-s).
|
||||
Normally nothing is output when that happens. */
|
||||
EXTERN int print_file_same_flag;
|
||||
|
||||
/* Output the differences with exactly 8 columns added to each line
|
||||
so that any tabs in the text line up properly (-T). */
|
||||
EXTERN int tab_align_flag;
|
||||
|
||||
/* Expand tabs in the output so the text lines up properly
|
||||
despite the characters added to the front of each line (-t). */
|
||||
EXTERN int tab_expand_flag;
|
||||
|
||||
/* In directory comparison, specify file to start with (-S).
|
||||
All file names less than this name are ignored. */
|
||||
EXTERN char *dir_start_file;
|
||||
|
||||
/* If a file is new (appears in only one dir)
|
||||
include its entire contents (-N).
|
||||
Then `patch' would create the file with appropriate contents. */
|
||||
EXTERN int entire_new_file_flag;
|
||||
|
||||
/* If a file is new (appears in only the second dir)
|
||||
include its entire contents (-P).
|
||||
Then `patch' would create the file with appropriate contents. */
|
||||
EXTERN int unidirectional_new_file_flag;
|
||||
|
||||
/* Pipe each file's output through pr (-l). */
|
||||
EXTERN int paginate_flag;
|
||||
|
||||
enum line_class {
|
||||
/* Lines taken from just the first file. */
|
||||
OLD,
|
||||
/* Lines taken from just the second file. */
|
||||
NEW,
|
||||
/* Lines common to both files. */
|
||||
UNCHANGED,
|
||||
/* A hunk containing both old and new lines (line groups only). */
|
||||
CHANGED
|
||||
};
|
||||
|
||||
/* Line group formats for old, new, unchanged, and changed groups. */
|
||||
EXTERN char *group_format[CHANGED + 1];
|
||||
|
||||
/* Line formats for old, new, and unchanged lines. */
|
||||
EXTERN char *line_format[UNCHANGED + 1];
|
||||
|
||||
/* If using OUTPUT_SDIFF print extra information to help the sdiff filter. */
|
||||
EXTERN int sdiff_help_sdiff;
|
||||
|
||||
/* Tell OUTPUT_SDIFF to show only the left version of common lines. */
|
||||
EXTERN int sdiff_left_only;
|
||||
|
||||
/* Tell OUTPUT_SDIFF to not show common lines. */
|
||||
EXTERN int sdiff_skip_common_lines;
|
||||
|
||||
/* The half line width and column 2 offset for OUTPUT_SDIFF. */
|
||||
EXTERN unsigned sdiff_half_width;
|
||||
EXTERN unsigned sdiff_column2_offset;
|
||||
|
||||
/* String containing all the command options diff received,
|
||||
with spaces between and at the beginning but none at the end.
|
||||
If there were no options given, this string is empty. */
|
||||
EXTERN char * switch_string;
|
||||
|
||||
/* Nonzero means use heuristics for better speed. */
|
||||
EXTERN int heuristic;
|
||||
|
||||
/* Name of program the user invoked (for error messages). */
|
||||
EXTERN char *diff_program_name;
|
||||
|
||||
/* Jump buffer for nonlocal exits. */
|
||||
EXTERN jmp_buf diff_abort_buf;
|
||||
#define DIFF_ABORT(retval) longjmp(diff_abort_buf, retval)
|
||||
|
||||
/* The result of comparison is an "edit script": a chain of `struct change'.
|
||||
Each `struct change' represents one place where some lines are deleted
|
||||
and some are inserted.
|
||||
|
||||
LINE0 and LINE1 are the first affected lines in the two files (origin 0).
|
||||
DELETED is the number of lines deleted here from file 0.
|
||||
INSERTED is the number of lines inserted here in file 1.
|
||||
|
||||
If DELETED is 0 then LINE0 is the number of the line before
|
||||
which the insertion was done; vice versa for INSERTED and LINE1. */
|
||||
|
||||
struct change
|
||||
{
|
||||
struct change *link; /* Previous or next edit command */
|
||||
int inserted; /* # lines of file 1 changed here. */
|
||||
int deleted; /* # lines of file 0 changed here. */
|
||||
int line0; /* Line number of 1st deleted line. */
|
||||
int line1; /* Line number of 1st inserted line. */
|
||||
char ignore; /* Flag used in context.c */
|
||||
};
|
||||
|
||||
/* Structures that describe the input files. */
|
||||
|
||||
/* Data on one input file being compared. */
|
||||
|
||||
struct file_data {
|
||||
int desc; /* File descriptor */
|
||||
char const *name; /* File name */
|
||||
struct stat stat; /* File status from fstat() */
|
||||
int dir_p; /* nonzero if file is a directory */
|
||||
|
||||
/* Buffer in which text of file is read. */
|
||||
char * buffer;
|
||||
/* Allocated size of buffer. */
|
||||
size_t bufsize;
|
||||
/* Number of valid characters now in the buffer. */
|
||||
size_t buffered_chars;
|
||||
|
||||
/* Array of pointers to lines in the file. */
|
||||
char const **linbuf;
|
||||
|
||||
/* linbuf_base <= buffered_lines <= valid_lines <= alloc_lines.
|
||||
linebuf[linbuf_base ... buffered_lines - 1] are possibly differing.
|
||||
linebuf[linbuf_base ... valid_lines - 1] contain valid data.
|
||||
linebuf[linbuf_base ... alloc_lines - 1] are allocated. */
|
||||
int linbuf_base, buffered_lines, valid_lines, alloc_lines;
|
||||
|
||||
/* Pointer to end of prefix of this file to ignore when hashing. */
|
||||
char const *prefix_end;
|
||||
|
||||
/* Count of lines in the prefix.
|
||||
There are this many lines in the file before linbuf[0]. */
|
||||
int prefix_lines;
|
||||
|
||||
/* Pointer to start of suffix of this file to ignore when hashing. */
|
||||
char const *suffix_begin;
|
||||
|
||||
/* Vector, indexed by line number, containing an equivalence code for
|
||||
each line. It is this vector that is actually compared with that
|
||||
of another file to generate differences. */
|
||||
int *equivs;
|
||||
|
||||
/* Vector, like the previous one except that
|
||||
the elements for discarded lines have been squeezed out. */
|
||||
int *undiscarded;
|
||||
|
||||
/* Vector mapping virtual line numbers (not counting discarded lines)
|
||||
to real ones (counting those lines). Both are origin-0. */
|
||||
int *realindexes;
|
||||
|
||||
/* Total number of nondiscarded lines. */
|
||||
int nondiscarded_lines;
|
||||
|
||||
/* Vector, indexed by real origin-0 line number,
|
||||
containing 1 for a line that is an insertion or a deletion.
|
||||
The results of comparison are stored here. */
|
||||
char *changed_flag;
|
||||
|
||||
/* 1 if file ends in a line with no final newline. */
|
||||
int missing_newline;
|
||||
|
||||
/* 1 more than the maximum equivalence value used for this or its
|
||||
sibling file. */
|
||||
int equiv_max;
|
||||
};
|
||||
|
||||
/* Describe the two files currently being compared. */
|
||||
|
||||
EXTERN struct file_data files[2];
|
||||
|
||||
/* Stdio stream to output diffs to. */
|
||||
|
||||
EXTERN FILE *outfile;
|
||||
|
||||
/* Declare various functions. */
|
||||
|
||||
/* analyze.c */
|
||||
int diff_2_files PARAMS((struct file_data[], int));
|
||||
|
||||
/* context.c */
|
||||
void print_context_header PARAMS((struct file_data[], int));
|
||||
void print_context_script PARAMS((struct change *, int));
|
||||
|
||||
/* diff.c */
|
||||
int excluded_filename PARAMS((char const *));
|
||||
|
||||
/* dir.c */
|
||||
int diff_dirs PARAMS((struct file_data const[], int (*) PARAMS((char const *, char const *, char const *, char const *, int)), int));
|
||||
|
||||
/* ed.c */
|
||||
void print_ed_script PARAMS((struct change *));
|
||||
void pr_forward_ed_script PARAMS((struct change *));
|
||||
|
||||
/* ifdef.c */
|
||||
void print_ifdef_script PARAMS((struct change *));
|
||||
|
||||
/* io.c */
|
||||
int read_files PARAMS((struct file_data[], int));
|
||||
int sip PARAMS((struct file_data *, int));
|
||||
void slurp PARAMS((struct file_data *));
|
||||
|
||||
/* normal.c */
|
||||
void print_normal_script PARAMS((struct change *));
|
||||
|
||||
/* rcs.c */
|
||||
void print_rcs_script PARAMS((struct change *));
|
||||
|
||||
/* side.c */
|
||||
void print_sdiff_script PARAMS((struct change *));
|
||||
|
||||
/* util.c */
|
||||
VOID *xmalloc PARAMS((size_t));
|
||||
VOID *xrealloc PARAMS((VOID *, size_t));
|
||||
char *concat PARAMS((char const *, char const *, char const *));
|
||||
char *dir_file_pathname PARAMS((char const *, char const *));
|
||||
int change_letter PARAMS((int, int));
|
||||
int line_cmp PARAMS((char const *, char const *));
|
||||
int translate_line_number PARAMS((struct file_data const *, int));
|
||||
struct change *find_change PARAMS((struct change *));
|
||||
struct change *find_reverse_change PARAMS((struct change *));
|
||||
void analyze_hunk PARAMS((struct change *, int *, int *, int *, int *, int *, int *));
|
||||
void begin_output PARAMS((void));
|
||||
void debug_script PARAMS((struct change *));
|
||||
void diff_error PARAMS((char const *, char const *, char const *));
|
||||
void fatal PARAMS((char const *));
|
||||
void finish_output PARAMS((void));
|
||||
void message PARAMS((char const *, char const *, char const *));
|
||||
void message5 PARAMS((char const *, char const *, char const *, char const *, char const *));
|
||||
void output_1_line PARAMS((char const *, char const *, char const *, char const *));
|
||||
void perror_with_name PARAMS((char const *));
|
||||
void pfatal_with_name PARAMS((char const *));
|
||||
void print_1_line PARAMS((char const *, char const * const *));
|
||||
void print_message_queue PARAMS((void));
|
||||
void print_number_range PARAMS((int, struct file_data *, int, int));
|
||||
void print_script PARAMS((struct change *, struct change * (*) PARAMS((struct change *)), void (*) PARAMS((struct change *))));
|
||||
void setup_output PARAMS((char const *, char const *, int));
|
||||
void translate_range PARAMS((struct file_data const *, int, int, int *, int *));
|
||||
|
||||
/* version.c */
|
||||
extern char const diff_version_string[];
|
||||
File diff suppressed because it is too large.
Load diff
@@ -1,220 +0,0 @@
|
||||
/* Read, sort and compare two directories. Used for GNU DIFF.
|
||||
Copyright (C) 1988, 1989, 1992, 1993, 1994 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
/* Read the directory named by DIR and store into DIRDATA a sorted vector
|
||||
of filenames for its contents. DIR->desc == -1 means this directory is
|
||||
known to be nonexistent, so set DIRDATA to an empty vector.
|
||||
Return -1 (setting errno) if error, 0 otherwise. */
|
||||
|
||||
struct dirdata
|
||||
{
|
||||
char const **names; /* Sorted names of files in dir, 0-terminated. */
|
||||
char *data; /* Allocated storage for file names. */
|
||||
};
|
||||
|
||||
static int compare_names PARAMS((void const *, void const *));
|
||||
static int dir_sort PARAMS((struct file_data const *, struct dirdata *));
|
||||
|
||||
#ifdef _WIN32
|
||||
#define CLOSEDIR_VOID 1
|
||||
#endif
|
||||
|
||||
static int
|
||||
dir_sort (dir, dirdata)
|
||||
struct file_data const *dir;
|
||||
struct dirdata *dirdata;
|
||||
{
|
||||
register struct dirent *next;
|
||||
register int i;
|
||||
|
||||
/* Address of block containing the files that are described. */
|
||||
char const **names;
|
||||
|
||||
/* Number of files in directory. */
|
||||
size_t nnames;
|
||||
|
||||
/* Allocated and used storage for file name data. */
|
||||
char *data;
|
||||
size_t data_alloc, data_used;
|
||||
|
||||
dirdata->names = 0;
|
||||
dirdata->data = 0;
|
||||
nnames = 0;
|
||||
data = 0;
|
||||
|
||||
if (dir->desc != -1)
|
||||
{
|
||||
/* Open the directory and check for errors. */
|
||||
register DIR *reading = opendir (dir->name);
|
||||
if (!reading)
|
||||
return -1;
|
||||
|
||||
/* Initialize the table of filenames. */
|
||||
|
||||
data_alloc = max (1, (size_t) dir->stat.st_size);
|
||||
data_used = 0;
|
||||
dirdata->data = data = xmalloc (data_alloc);
|
||||
|
||||
/* Read the directory entries, and insert the subfiles
|
||||
into the `data' table. */
|
||||
|
||||
while ((errno = 0, (next = readdir (reading)) != 0))
|
||||
{
|
||||
char *d_name = next->d_name;
|
||||
size_t d_size = NAMLEN (next) + 1;
|
||||
|
||||
/* Ignore the files `.' and `..' */
|
||||
if (d_name[0] == '.'
|
||||
&& (d_name[1] == 0 || (d_name[1] == '.' && d_name[2] == 0)))
|
||||
continue;
|
||||
|
||||
if (excluded_filename (d_name))
|
||||
continue;
|
||||
|
||||
while (data_alloc < data_used + d_size)
|
||||
dirdata->data = data = xrealloc (data, data_alloc *= 2);
|
||||
memcpy (data + data_used, d_name, d_size);
|
||||
data_used += d_size;
|
||||
nnames++;
|
||||
}
|
||||
if (errno)
|
||||
{
|
||||
int e = errno;
|
||||
closedir (reading);
|
||||
errno = e;
|
||||
return -1;
|
||||
}
|
||||
#if CLOSEDIR_VOID
|
||||
closedir (reading);
|
||||
#else
|
||||
if (closedir (reading) != 0)
|
||||
return -1;
|
||||
#endif
|
||||
}
|
||||
|
||||
/* Create the `names' table from the `data' table. */
|
||||
dirdata->names = names = (char const **) xmalloc (sizeof (char *)
|
||||
* (nnames + 1));
|
||||
for (i = 0; i < nnames; i++)
|
||||
{
|
||||
names[i] = data;
|
||||
data += strlen (data) + 1;
|
||||
}
|
||||
names[nnames] = 0;
|
||||
|
||||
/* Sort the table. */
|
||||
qsort (names, nnames, sizeof (char *), compare_names);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Sort the files now in the table. */
|
||||
|
||||
static int
|
||||
compare_names (file1, file2)
|
||||
void const *file1, *file2;
|
||||
{
|
||||
return filename_cmp (* (char const *const *) file1,
|
||||
* (char const *const *) file2);
|
||||
}
|
||||
|
||||
/* Compare the contents of two directories named in FILEVEC[0] and FILEVEC[1].
|
||||
This is a top-level routine; it does everything necessary for diff
|
||||
on two directories.
|
||||
|
||||
FILEVEC[0].desc == -1 says directory FILEVEC[0] doesn't exist,
|
||||
but pretend it is empty. Likewise for FILEVEC[1].
|
||||
|
||||
HANDLE_FILE is a caller-provided subroutine called to handle each file.
|
||||
It gets five operands: dir and name (rel to original working dir) of file
|
||||
in dir 0, dir and name pathname of file in dir 1, and the recursion depth.
|
||||
|
||||
For a file that appears in only one of the dirs, one of the name-args
|
||||
to HANDLE_FILE is zero.
|
||||
|
||||
DEPTH is the current depth in recursion, used for skipping top-level
|
||||
files by the -S option.
|
||||
|
||||
Returns the maximum of all the values returned by HANDLE_FILE,
|
||||
or 2 if trouble is encountered in opening files. */
|
||||
|
||||
int
|
||||
diff_dirs (filevec, handle_file, depth)
|
||||
struct file_data const filevec[];
|
||||
int (*handle_file) PARAMS((char const *, char const *, char const *, char const *, int));
|
||||
int depth;
|
||||
{
|
||||
struct dirdata dirdata[2];
|
||||
int val = 0; /* Return value. */
|
||||
int i;
|
||||
|
||||
/* Get sorted contents of both dirs. */
|
||||
for (i = 0; i < 2; i++)
|
||||
if (dir_sort (&filevec[i], &dirdata[i]) != 0)
|
||||
{
|
||||
perror_with_name (filevec[i].name);
|
||||
val = 2;
|
||||
}
|
||||
|
||||
if (val == 0)
|
||||
{
|
||||
register char const * const *names0 = dirdata[0].names;
|
||||
register char const * const *names1 = dirdata[1].names;
|
||||
char const *name0 = filevec[0].name;
|
||||
char const *name1 = filevec[1].name;
|
||||
|
||||
/* If `-S name' was given, and this is the topmost level of comparison,
|
||||
ignore all file names less than the specified starting name. */
|
||||
|
||||
if (dir_start_file && depth == 0)
|
||||
{
|
||||
while (*names0 && filename_cmp (*names0, dir_start_file) < 0)
|
||||
names0++;
|
||||
while (*names1 && filename_cmp (*names1, dir_start_file) < 0)
|
||||
names1++;
|
||||
}
|
||||
|
||||
/* Loop while files remain in one or both dirs. */
|
||||
while (*names0 || *names1)
|
||||
{
|
||||
/* Compare next name in dir 0 with next name in dir 1.
|
||||
At the end of a dir,
|
||||
pretend the "next name" in that dir is very large. */
|
||||
int nameorder = (!*names0 ? 1 : !*names1 ? -1
|
||||
: filename_cmp (*names0, *names1));
|
||||
int v1 = (*handle_file) (name0, 0 < nameorder ? 0 : *names0++,
|
||||
name1, nameorder < 0 ? 0 : *names1++,
|
||||
depth + 1);
|
||||
if (v1 > val)
|
||||
val = v1;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < 2; i++)
|
||||
{
|
||||
if (dirdata[i].names)
|
||||
free (dirdata[i].names);
|
||||
if (dirdata[i].data)
|
||||
free (dirdata[i].data);
|
||||
}
|
||||
|
||||
return val;
|
||||
}
|
||||
@@ -1,200 +0,0 @@
|
||||
/* Output routines for ed-script format.
|
||||
Copyright (C) 1988, 89, 91, 92, 93 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
static void print_ed_hunk PARAMS((struct change *));
|
||||
static void print_rcs_hunk PARAMS((struct change *));
|
||||
static void pr_forward_ed_hunk PARAMS((struct change *));
|
||||
|
||||
/* Print our script as ed commands. */
|
||||
|
||||
void
|
||||
print_ed_script (script)
|
||||
struct change *script;
|
||||
{
|
||||
print_script (script, find_reverse_change, print_ed_hunk);
|
||||
}
|
||||
|
||||
/* Print a hunk of an ed diff */
|
||||
|
||||
static void
|
||||
print_ed_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int f0, l0, f1, l1;
|
||||
int deletes, inserts;
|
||||
|
||||
#if 0
|
||||
hunk = flip_script (hunk);
|
||||
#endif
|
||||
#ifdef DEBUG
|
||||
debug_script (hunk);
|
||||
#endif
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
analyze_hunk (hunk, &f0, &l0, &f1, &l1, &deletes, &inserts);
|
||||
if (!deletes && !inserts)
|
||||
return;
|
||||
|
||||
begin_output ();
|
||||
|
||||
/* Print out the line number header for this hunk */
|
||||
print_number_range (',', &files[0], f0, l0);
|
||||
fprintf (outfile, "%c\n", change_letter (inserts, deletes));
|
||||
|
||||
/* Print new/changed lines from second file, if needed */
|
||||
if (inserts)
|
||||
{
|
||||
int i;
|
||||
int inserting = 1;
|
||||
for (i = f1; i <= l1; i++)
|
||||
{
|
||||
/* Resume the insert, if we stopped. */
|
||||
if (! inserting)
|
||||
fprintf (outfile, "%da\n",
|
||||
i - f1 + translate_line_number (&files[0], f0) - 1);
|
||||
inserting = 1;
|
||||
|
||||
/* If the file's line is just a dot, it would confuse `ed'.
|
||||
So output it with a double dot, and set the flag LEADING_DOT
|
||||
so that we will output another ed-command later
|
||||
to change the double dot into a single dot. */
|
||||
|
||||
if (files[1].linbuf[i][0] == '.'
|
||||
&& files[1].linbuf[i][1] == '\n')
|
||||
{
|
||||
fprintf (outfile, "..\n");
|
||||
fprintf (outfile, ".\n");
|
||||
/* Now change that double dot to the desired single dot. */
|
||||
fprintf (outfile, "%ds/^\\.\\././\n",
|
||||
i - f1 + translate_line_number (&files[0], f0));
|
||||
inserting = 0;
|
||||
}
|
||||
else
|
||||
/* Line is not `.', so output it unmodified. */
|
||||
print_1_line ("", &files[1].linbuf[i]);
|
||||
}
|
||||
|
||||
/* End insert mode, if we are still in it. */
|
||||
if (inserting)
|
||||
fprintf (outfile, ".\n");
|
||||
}
|
||||
}
|
||||
|
||||
/* Print change script in the style of ed commands,
|
||||
but print the changes in the order they appear in the input files,
|
||||
which means that the commands are not truly useful with ed. */
|
||||
|
||||
void
|
||||
pr_forward_ed_script (script)
|
||||
struct change *script;
|
||||
{
|
||||
print_script (script, find_change, pr_forward_ed_hunk);
|
||||
}
|
||||
|
||||
static void
|
||||
pr_forward_ed_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int i;
|
||||
int f0, l0, f1, l1;
|
||||
int deletes, inserts;
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
analyze_hunk (hunk, &f0, &l0, &f1, &l1, &deletes, &inserts);
|
||||
if (!deletes && !inserts)
|
||||
return;
|
||||
|
||||
begin_output ();
|
||||
|
||||
fprintf (outfile, "%c", change_letter (inserts, deletes));
|
||||
print_number_range (' ', files, f0, l0);
|
||||
fprintf (outfile, "\n");
|
||||
|
||||
/* If deletion only, print just the number range. */
|
||||
|
||||
if (!inserts)
|
||||
return;
|
||||
|
||||
/* For insertion (with or without deletion), print the number range
|
||||
and the lines from file 2. */
|
||||
|
||||
for (i = f1; i <= l1; i++)
|
||||
print_1_line ("", &files[1].linbuf[i]);
|
||||
|
||||
fprintf (outfile, ".\n");
|
||||
}
|
||||
|
||||
/* Print in a format somewhat like ed commands
|
||||
except that each insert command states the number of lines it inserts.
|
||||
This format is used for RCS. */
|
||||
|
||||
void
|
||||
print_rcs_script (script)
|
||||
struct change *script;
|
||||
{
|
||||
print_script (script, find_change, print_rcs_hunk);
|
||||
}
|
||||
|
||||
/* Print a hunk of an RCS diff */
|
||||
|
||||
static void
|
||||
print_rcs_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int i;
|
||||
int f0, l0, f1, l1;
|
||||
int deletes, inserts;
|
||||
int tf0, tl0, tf1, tl1;
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
analyze_hunk (hunk, &f0, &l0, &f1, &l1, &deletes, &inserts);
|
||||
if (!deletes && !inserts)
|
||||
return;
|
||||
|
||||
begin_output ();
|
||||
|
||||
translate_range (&files[0], f0, l0, &tf0, &tl0);
|
||||
|
||||
if (deletes)
|
||||
{
|
||||
fprintf (outfile, "d");
|
||||
/* For deletion, print just the starting line number from file 0
|
||||
and the number of lines deleted. */
|
||||
fprintf (outfile, "%d %d\n",
|
||||
tf0,
|
||||
(tl0 >= tf0 ? tl0 - tf0 + 1 : 1));
|
||||
}
|
||||
|
||||
if (inserts)
|
||||
{
|
||||
fprintf (outfile, "a");
|
||||
|
||||
/* Take last-line-number from file 0 and # lines from file 1. */
|
||||
translate_range (&files[1], f1, l1, &tf1, &tl1);
|
||||
fprintf (outfile, "%d %d\n",
|
||||
tl0,
|
||||
(tl1 >= tf1 ? tl1 - tf1 + 1 : 1));
|
||||
|
||||
/* Print the inserted lines. */
|
||||
for (i = f1; i <= l1; i++)
|
||||
print_1_line ("", &files[1].linbuf[i]);
|
||||
}
|
||||
}
|
||||
@@ -1,428 +0,0 @@
|
||||
/* #ifdef-format output routines for GNU DIFF.
|
||||
Copyright (C) 1989, 1991, 1992, 1993, 1994 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY. No author or distributor
|
||||
accepts responsibility to anyone for the consequences of using it
|
||||
or for whether it serves any particular purpose or works at all,
|
||||
unless he says so in writing. Refer to the GNU DIFF General Public
|
||||
License for full details.
|
||||
|
||||
Everyone is granted permission to copy, modify and redistribute
|
||||
GNU DIFF, but only under the conditions described in the
|
||||
GNU DIFF General Public License. A copy of this license is
|
||||
supposed to have been given to you along with GNU DIFF so you
|
||||
can know your rights and responsibilities. It should be in a
|
||||
file named COPYING. Among other things, the copyright notice
|
||||
and this notice must be preserved on all copies. */
|
||||
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
struct group
|
||||
{
|
||||
struct file_data const *file;
|
||||
int from, upto; /* start and limit lines for this group of lines */
|
||||
};
|
||||
|
||||
static char *format_group PARAMS((FILE *, char *, int, struct group const *));
|
||||
static char *scan_char_literal PARAMS((char *, int *));
|
||||
static char *scan_printf_spec PARAMS((char *));
|
||||
static int groups_letter_value PARAMS((struct group const *, int));
|
||||
static void format_ifdef PARAMS((char *, int, int, int, int));
|
||||
static void print_ifdef_hunk PARAMS((struct change *));
|
||||
static void print_ifdef_lines PARAMS((FILE *, char *, struct group const *));
|
||||
|
||||
static int next_line;
|
||||
|
||||
/* Print the edit-script SCRIPT as a merged #ifdef file. */
|
||||
|
||||
void
|
||||
print_ifdef_script (script)
|
||||
struct change *script;
|
||||
{
|
||||
next_line = - files[0].prefix_lines;
|
||||
print_script (script, find_change, print_ifdef_hunk);
|
||||
if (next_line < files[0].valid_lines)
|
||||
{
|
||||
begin_output ();
|
||||
format_ifdef (group_format[UNCHANGED], next_line, files[0].valid_lines,
|
||||
next_line - files[0].valid_lines + files[1].valid_lines,
|
||||
files[1].valid_lines);
|
||||
}
|
||||
}
|
||||
|
||||
/* Print a hunk of an ifdef diff.
|
||||
This is a contiguous portion of a complete edit script,
|
||||
describing changes in consecutive lines. */
|
||||
|
||||
static void
|
||||
print_ifdef_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int first0, last0, first1, last1, deletes, inserts;
|
||||
char *format;
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
analyze_hunk (hunk, &first0, &last0, &first1, &last1, &deletes, &inserts);
|
||||
if (inserts)
|
||||
format = deletes ? group_format[CHANGED] : group_format[NEW];
|
||||
else if (deletes)
|
||||
format = group_format[OLD];
|
||||
else
|
||||
return;
|
||||
|
||||
begin_output ();
|
||||
|
||||
/* Print lines up to this change. */
|
||||
if (next_line < first0)
|
||||
format_ifdef (group_format[UNCHANGED], next_line, first0,
|
||||
next_line - first0 + first1, first1);
|
||||
|
||||
/* Print this change. */
|
||||
next_line = last0 + 1;
|
||||
format_ifdef (format, first0, next_line, first1, last1 + 1);
|
||||
}
|
||||
|
||||
/* Print a set of lines according to FORMAT.
|
||||
Lines BEG0 up to END0 are from the first file;
|
||||
lines BEG1 up to END1 are from the second file. */
|
||||
|
||||
static void
|
||||
format_ifdef (format, beg0, end0, beg1, end1)
|
||||
char *format;
|
||||
int beg0, end0, beg1, end1;
|
||||
{
|
||||
struct group groups[2];
|
||||
|
||||
groups[0].file = &files[0];
|
||||
groups[0].from = beg0;
|
||||
groups[0].upto = end0;
|
||||
groups[1].file = &files[1];
|
||||
groups[1].from = beg1;
|
||||
groups[1].upto = end1;
|
||||
format_group (outfile, format, '\0', groups);
|
||||
}
|
||||
|
||||
/* Print to file OUT a set of lines according to FORMAT.
|
||||
The format ends at the first free instance of ENDCHAR.
|
||||
Yield the address of the terminating character.
|
||||
GROUPS specifies which lines to print.
|
||||
If OUT is zero, do not actually print anything; just scan the format. */
|
||||
|
||||
static char *
|
||||
format_group (out, format, endchar, groups)
|
||||
register FILE *out;
|
||||
char *format;
|
||||
int endchar;
|
||||
struct group const *groups;
|
||||
{
|
||||
register char c;
|
||||
register char *f = format;
|
||||
|
||||
while ((c = *f) != endchar && c != 0)
|
||||
{
|
||||
f++;
|
||||
if (c == '%')
|
||||
{
|
||||
char *spec = f;
|
||||
switch ((c = *f++))
|
||||
{
|
||||
case '%':
|
||||
break;
|
||||
|
||||
case '(':
|
||||
/* Print if-then-else format e.g. `%(n=1?thenpart:elsepart)'. */
|
||||
{
|
||||
int i, value[2];
|
||||
FILE *thenout, *elseout;
|
||||
|
||||
for (i = 0; i < 2; i++)
|
||||
{
|
||||
unsigned char f0 = f[0];
|
||||
if (ISDIGIT (f0))
|
||||
{
|
||||
value[i] = atoi (f);
|
||||
while (ISDIGIT ((unsigned char) *++f))
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
value[i] = groups_letter_value (groups, f0);
|
||||
if (value[i] < 0)
|
||||
goto bad_format;
|
||||
f++;
|
||||
}
|
||||
if (*f++ != "=?"[i])
|
||||
goto bad_format;
|
||||
}
|
||||
if (value[0] == value[1])
|
||||
thenout = out, elseout = 0;
|
||||
else
|
||||
thenout = 0, elseout = out;
|
||||
f = format_group (thenout, f, ':', groups);
|
||||
if (*f)
|
||||
{
|
||||
f = format_group (elseout, f + 1, ')', groups);
|
||||
if (*f)
|
||||
f++;
|
||||
}
|
||||
}
|
||||
continue;
|
||||
|
||||
case '<':
|
||||
/* Print lines deleted from first file. */
|
||||
print_ifdef_lines (out, line_format[OLD], &groups[0]);
|
||||
continue;
|
||||
|
||||
case '=':
|
||||
/* Print common lines. */
|
||||
print_ifdef_lines (out, line_format[UNCHANGED], &groups[0]);
|
||||
continue;
|
||||
|
||||
case '>':
|
||||
/* Print lines inserted from second file. */
|
||||
print_ifdef_lines (out, line_format[NEW], &groups[1]);
|
||||
continue;
|
||||
|
||||
default:
|
||||
{
|
||||
int value;
|
||||
char *speclim;
|
||||
|
||||
f = scan_printf_spec (spec);
|
||||
if (!f)
|
||||
goto bad_format;
|
||||
speclim = f;
|
||||
c = *f++;
|
||||
switch (c)
|
||||
{
|
||||
case '\'':
|
||||
f = scan_char_literal (f, &value);
|
||||
if (!f)
|
||||
goto bad_format;
|
||||
break;
|
||||
|
||||
default:
|
||||
value = groups_letter_value (groups, c);
|
||||
if (value < 0)
|
||||
goto bad_format;
|
||||
break;
|
||||
}
|
||||
if (out)
|
||||
{
|
||||
/* Temporarily replace e.g. "%3dnx" with "%3d\0x". */
|
||||
*speclim = 0;
|
||||
fprintf (out, spec - 1, value);
|
||||
/* Undo the temporary replacement. */
|
||||
*speclim = c;
|
||||
}
|
||||
}
|
||||
continue;
|
||||
|
||||
bad_format:
|
||||
c = '%';
|
||||
f = spec;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (out)
|
||||
putc (c, out);
|
||||
}
|
||||
return f;
|
||||
}
|
||||
|
||||
/* For the line group pair G, return the number corresponding to LETTER.
|
||||
Return -1 if LETTER is not a group format letter. */
|
||||
static int
|
||||
groups_letter_value (g, letter)
|
||||
struct group const *g;
|
||||
int letter;
|
||||
{
|
||||
if (ISUPPER (letter))
|
||||
{
|
||||
g++;
|
||||
letter = tolower (letter);
|
||||
}
|
||||
switch (letter)
|
||||
{
|
||||
case 'e': return translate_line_number (g->file, g->from) - 1;
|
||||
case 'f': return translate_line_number (g->file, g->from);
|
||||
case 'l': return translate_line_number (g->file, g->upto) - 1;
|
||||
case 'm': return translate_line_number (g->file, g->upto);
|
||||
case 'n': return g->upto - g->from;
|
||||
default: return -1;
|
||||
}
|
||||
}
|
||||
|
||||
/* Print to file OUT, using FORMAT to print the line group GROUP.
|
||||
But do nothing if OUT is zero. */
|
||||
static void
|
||||
print_ifdef_lines (out, format, group)
|
||||
register FILE *out;
|
||||
char *format;
|
||||
struct group const *group;
|
||||
{
|
||||
struct file_data const *file = group->file;
|
||||
char const * const *linbuf = file->linbuf;
|
||||
int from = group->from, upto = group->upto;
|
||||
|
||||
if (!out)
|
||||
return;
|
||||
|
||||
/* If possible, use a single fwrite; it's faster. */
|
||||
if (!tab_expand_flag && format[0] == '%')
|
||||
{
|
||||
if (format[1] == 'l' && format[2] == '\n' && !format[3])
|
||||
{
|
||||
fwrite (linbuf[from], sizeof (char),
|
||||
linbuf[upto] + (linbuf[upto][-1] != '\n') - linbuf[from],
|
||||
out);
|
||||
return;
|
||||
}
|
||||
if (format[1] == 'L' && !format[2])
|
||||
{
|
||||
fwrite (linbuf[from], sizeof (char),
|
||||
linbuf[upto] - linbuf[from], out);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
for (; from < upto; from++)
|
||||
{
|
||||
register char c;
|
||||
register char *f = format;
|
||||
|
||||
while ((c = *f++) != 0)
|
||||
{
|
||||
if (c == '%')
|
||||
{
|
||||
char *spec = f;
|
||||
switch ((c = *f++))
|
||||
{
|
||||
case '%':
|
||||
break;
|
||||
|
||||
case 'l':
|
||||
output_1_line (linbuf[from],
|
||||
linbuf[from + 1]
|
||||
- (linbuf[from + 1][-1] == '\n'), 0, 0);
|
||||
continue;
|
||||
|
||||
case 'L':
|
||||
output_1_line (linbuf[from], linbuf[from + 1], 0, 0);
|
||||
continue;
|
||||
|
||||
default:
|
||||
{
|
||||
int value;
|
||||
char *speclim;
|
||||
|
||||
f = scan_printf_spec (spec);
|
||||
if (!f)
|
||||
goto bad_format;
|
||||
speclim = f;
|
||||
c = *f++;
|
||||
switch (c)
|
||||
{
|
||||
case '\'':
|
||||
f = scan_char_literal (f, &value);
|
||||
if (!f)
|
||||
goto bad_format;
|
||||
break;
|
||||
|
||||
case 'n':
|
||||
value = translate_line_number (file, from);
|
||||
break;
|
||||
|
||||
default:
|
||||
goto bad_format;
|
||||
}
|
||||
/* Temporarily replace e.g. "%3dnx" with "%3d\0x". */
|
||||
*speclim = 0;
|
||||
fprintf (out, spec - 1, value);
|
||||
/* Undo the temporary replacement. */
|
||||
*speclim = c;
|
||||
}
|
||||
continue;
|
||||
|
||||
bad_format:
|
||||
c = '%';
|
||||
f = spec;
|
||||
break;
|
||||
}
|
||||
}
|
||||
putc (c, out);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Scan the character literal represented in the string LIT; LIT points just
|
||||
after the initial apostrophe. Put the literal's value into *INTPTR.
|
||||
Yield the address of the first character after the closing apostrophe,
|
||||
or zero if the literal is ill-formed. */
|
||||
static char *
|
||||
scan_char_literal (lit, intptr)
|
||||
char *lit;
|
||||
int *intptr;
|
||||
{
|
||||
register char *p = lit;
|
||||
int value, digits;
|
||||
char c = *p++;
|
||||
|
||||
switch (c)
|
||||
{
|
||||
case 0:
|
||||
case '\'':
|
||||
return 0;
|
||||
|
||||
case '\\':
|
||||
value = 0;
|
||||
while ((c = *p++) != '\'')
|
||||
{
|
||||
unsigned digit = c - '0';
|
||||
if (8 <= digit)
|
||||
return 0;
|
||||
value = 8 * value + digit;
|
||||
}
|
||||
digits = p - lit - 2;
|
||||
if (! (1 <= digits && digits <= 3))
|
||||
return 0;
|
||||
break;
|
||||
|
||||
default:
|
||||
value = c;
|
||||
if (*p++ != '\'')
|
||||
return 0;
|
||||
break;
|
||||
}
|
||||
*intptr = value;
|
||||
return p;
|
||||
}
|
||||
|
||||
/* Scan optional printf-style SPEC of the form `-*[0-9]*(.[0-9]*)?[cdoxX]'.
|
||||
Return the address of the character following SPEC, or zero if failure. */
|
||||
static char *
|
||||
scan_printf_spec (spec)
|
||||
register char *spec;
|
||||
{
|
||||
register unsigned char c;
|
||||
|
||||
while ((c = *spec++) == '-')
|
||||
continue;
|
||||
while (ISDIGIT (c))
|
||||
c = *spec++;
|
||||
if (c == '.')
|
||||
while (ISDIGIT (c = *spec++))
|
||||
continue;
|
||||
switch (c)
|
||||
{
|
||||
case 'c': case 'd': case 'o': case 'x': case 'X':
|
||||
return spec;
|
||||
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
@@ -1,714 +0,0 @@
|
||||
/* File I/O for GNU DIFF.
|
||||
Copyright (C) 1988, 1989, 1992, 1993, 1994 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
/* Rotate a value n bits to the left. */
|
||||
#define UINT_BIT (sizeof (unsigned) * CHAR_BIT)
|
||||
#define ROL(v, n) ((v) << (n) | (v) >> (UINT_BIT - (n)))
|
||||
|
||||
/* Given a hash value and a new character, return a new hash value. */
|
||||
#define HASH(h, c) ((c) + ROL (h, 7))
|
||||
|
||||
/* Guess remaining number of lines from number N of lines so far,
|
||||
size S so far, and total size T. */
|
||||
#define GUESS_LINES(n,s,t) (((t) - (s)) / ((n) < 10 ? 32 : (s) / ((n)-1)) + 5)
|
||||
|
||||
/* Type used for fast prefix comparison in find_identical_ends. */
|
||||
#ifndef word
|
||||
#define word int
|
||||
#endif
|
||||
|
||||
/* Lines are put into equivalence classes (of lines that match in line_cmp).
|
||||
Each equivalence class is represented by one of these structures,
|
||||
but only while the classes are being computed.
|
||||
Afterward, each class is represented by a number. */
|
||||
struct equivclass
|
||||
{
|
||||
int next; /* Next item in this bucket. */
|
||||
unsigned hash; /* Hash of lines in this class. */
|
||||
char const *line; /* A line that fits this class. */
|
||||
size_t length; /* That line's length, not counting its newline. */
|
||||
};
|
||||
|
||||
/* Hash-table: array of buckets, each being a chain of equivalence classes.
|
||||
buckets[-1] is reserved for incomplete lines. */
|
||||
static int *buckets;
|
||||
|
||||
/* Number of buckets in the hash table array, not counting buckets[-1]. */
|
||||
static int nbuckets;
|
||||
|
||||
/* Array in which the equivalence classes are allocated.
|
||||
The bucket-chains go through the elements in this array.
|
||||
The number of an equivalence class is its index in this array. */
|
||||
static struct equivclass *equivs;
|
||||
|
||||
/* Index of first free element in the array `equivs'. */
|
||||
static int equivs_index;
|
||||
|
||||
/* Number of elements allocated in the array `equivs'. */
|
||||
static int equivs_alloc;
|
||||
|
||||
static void find_and_hash_each_line PARAMS((struct file_data *));
|
||||
static void find_identical_ends PARAMS((struct file_data[]));
|
||||
static void prepare_text_end PARAMS((struct file_data *));
|
||||
|
||||
/* Check for binary files and compare them for exact identity. */
|
||||
|
||||
/* Return 1 if BUF contains a non text character.
|
||||
SIZE is the number of characters in BUF. */
|
||||
|
||||
#define binary_file_p(buf, size) (memchr (buf, '\0', size) != 0)
|
||||
|
||||
/* Get ready to read the current file.
|
||||
Return nonzero if SKIP_TEST is zero,
|
||||
and if it appears to be a binary file. */
|
||||
|
||||
int
|
||||
sip (current, skip_test)
|
||||
struct file_data *current;
|
||||
int skip_test;
|
||||
{
|
||||
/* If we have a nonexistent file at this stage, treat it as empty. */
|
||||
if (current->desc < 0)
|
||||
{
|
||||
/* Leave room for a sentinel. */
|
||||
current->bufsize = sizeof (word);
|
||||
current->buffer = xmalloc (current->bufsize);
|
||||
}
|
||||
else
|
||||
{
|
||||
current->bufsize = STAT_BLOCKSIZE (current->stat);
|
||||
current->buffer = xmalloc (current->bufsize);
|
||||
|
||||
if (! skip_test)
|
||||
{
|
||||
/* Check first part of file to see if it's a binary file. */
|
||||
#if HAVE_SETMODE
|
||||
int oldmode = setmode (current->desc, O_BINARY);
|
||||
#endif
|
||||
size_t n = read (current->desc, current->buffer, current->bufsize);
|
||||
if (n == -1)
|
||||
pfatal_with_name (current->name);
|
||||
current->buffered_chars = n;
|
||||
#if HAVE_SETMODE
|
||||
if (oldmode != O_BINARY)
|
||||
{
|
||||
if (lseek (current->desc, - (off_t) n, SEEK_CUR) == -1)
|
||||
pfatal_with_name (current->name);
|
||||
setmode (current->desc, oldmode);
|
||||
current->buffered_chars = 0;
|
||||
}
|
||||
#endif
|
||||
return binary_file_p (current->buffer, n);
|
||||
}
|
||||
}
|
||||
|
||||
current->buffered_chars = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Slurp the rest of the current file completely into memory. */
|
||||
|
||||
void
|
||||
slurp (current)
|
||||
struct file_data *current;
|
||||
{
|
||||
size_t cc;
|
||||
|
||||
if (current->desc < 0)
|
||||
/* The file is nonexistent. */
|
||||
;
|
||||
else if (S_ISREG (current->stat.st_mode))
|
||||
{
|
||||
/* It's a regular file; slurp in the rest all at once. */
|
||||
|
||||
/* Get the size out of the stat block.
|
||||
Allocate enough room for appended newline and sentinel. */
|
||||
cc = current->stat.st_size + 1 + sizeof (word);
|
||||
if (current->bufsize < cc)
|
||||
{
|
||||
current->bufsize = cc;
|
||||
current->buffer = xrealloc (current->buffer, cc);
|
||||
}
|
||||
|
||||
if (current->buffered_chars < current->stat.st_size)
|
||||
{
|
||||
cc = read (current->desc,
|
||||
current->buffer + current->buffered_chars,
|
||||
current->stat.st_size - current->buffered_chars);
|
||||
if (cc == -1)
|
||||
pfatal_with_name (current->name);
|
||||
current->buffered_chars += cc;
|
||||
}
|
||||
}
|
||||
/* It's not a regular file; read it, growing the buffer as needed. */
|
||||
else if (always_text_flag || current->buffered_chars != 0)
|
||||
{
|
||||
for (;;)
|
||||
{
|
||||
if (current->buffered_chars == current->bufsize)
|
||||
{
|
||||
current->bufsize = current->bufsize * 2;
|
||||
current->buffer = xrealloc (current->buffer, current->bufsize);
|
||||
}
|
||||
cc = read (current->desc,
|
||||
current->buffer + current->buffered_chars,
|
||||
current->bufsize - current->buffered_chars);
|
||||
if (cc == 0)
|
||||
break;
|
||||
if (cc == -1)
|
||||
pfatal_with_name (current->name);
|
||||
current->buffered_chars += cc;
|
||||
}
|
||||
/* Allocate just enough room for appended newline and sentinel. */
|
||||
current->bufsize = current->buffered_chars + 1 + sizeof (word);
|
||||
current->buffer = xrealloc (current->buffer, current->bufsize);
|
||||
}
|
||||
}
|
||||
|
||||
/* Split the file into lines, simultaneously computing the equivalence class for
|
||||
each line. */
|
||||
|
||||
static void
|
||||
find_and_hash_each_line (current)
|
||||
struct file_data *current;
|
||||
{
|
||||
unsigned h;
|
||||
unsigned char const *p = (unsigned char const *) current->prefix_end;
|
||||
unsigned char c;
|
||||
int i, *bucket;
|
||||
size_t length;
|
||||
|
||||
/* Cache often-used quantities in local variables to help the compiler. */
|
||||
char const **linbuf = current->linbuf;
|
||||
int alloc_lines = current->alloc_lines;
|
||||
int line = 0;
|
||||
int linbuf_base = current->linbuf_base;
|
||||
int *cureqs = (int *) xmalloc (alloc_lines * sizeof (int));
|
||||
struct equivclass *eqs = equivs;
|
||||
int eqs_index = equivs_index;
|
||||
int eqs_alloc = equivs_alloc;
|
||||
char const *suffix_begin = current->suffix_begin;
|
||||
char const *bufend = current->buffer + current->buffered_chars;
|
||||
int use_line_cmp = ignore_some_line_changes;
|
||||
|
||||
while ((char const *) p < suffix_begin)
|
||||
{
|
||||
char const *ip = (char const *) p;
|
||||
|
||||
/* Compute the equivalence class for this line. */
|
||||
|
||||
h = 0;
|
||||
|
||||
/* Hash this line until we find a newline. */
|
||||
if (ignore_case_flag)
|
||||
{
|
||||
if (ignore_all_space_flag)
|
||||
while ((c = *p++) != '\n')
|
||||
{
|
||||
if (! ISSPACE (c))
|
||||
h = HASH (h, ISUPPER (c) ? tolower (c) : c);
|
||||
}
|
||||
else if (ignore_space_change_flag)
|
||||
while ((c = *p++) != '\n')
|
||||
{
|
||||
if (ISSPACE (c))
|
||||
{
|
||||
for (;;)
|
||||
{
|
||||
c = *p++;
|
||||
if (!ISSPACE (c))
|
||||
break;
|
||||
if (c == '\n')
|
||||
goto hashing_done;
|
||||
}
|
||||
h = HASH (h, ' ');
|
||||
}
|
||||
/* C is now the first non-space. */
|
||||
h = HASH (h, ISUPPER (c) ? tolower (c) : c);
|
||||
}
|
||||
else
|
||||
while ((c = *p++) != '\n')
|
||||
h = HASH (h, ISUPPER (c) ? tolower (c) : c);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ignore_all_space_flag)
|
||||
while ((c = *p++) != '\n')
|
||||
{
|
||||
if (! ISSPACE (c))
|
||||
h = HASH (h, c);
|
||||
}
|
||||
else if (ignore_space_change_flag)
|
||||
while ((c = *p++) != '\n')
|
||||
{
|
||||
if (ISSPACE (c))
|
||||
{
|
||||
for (;;)
|
||||
{
|
||||
c = *p++;
|
||||
if (!ISSPACE (c))
|
||||
break;
|
||||
if (c == '\n')
|
||||
goto hashing_done;
|
||||
}
|
||||
h = HASH (h, ' ');
|
||||
}
|
||||
/* C is now the first non-space. */
|
||||
h = HASH (h, c);
|
||||
}
|
||||
else
|
||||
while ((c = *p++) != '\n')
|
||||
h = HASH (h, c);
|
||||
}
|
||||
hashing_done:;
|
||||
|
||||
bucket = &buckets[h % nbuckets];
|
||||
length = (char const *) p - ip - 1;
|
||||
|
||||
if ((char const *) p == bufend
|
||||
&& current->missing_newline
|
||||
&& ROBUST_OUTPUT_STYLE (output_style))
|
||||
{
|
||||
/* This line is incomplete. If this is significant,
|
||||
put the line into bucket[-1]. */
|
||||
if (! (ignore_space_change_flag | ignore_all_space_flag))
|
||||
bucket = &buckets[-1];
|
||||
|
||||
/* Omit the inserted newline when computing linbuf later. */
|
||||
p--;
|
||||
bufend = suffix_begin = (char const *) p;
|
||||
}
|
||||
|
||||
for (i = *bucket; ; i = eqs[i].next)
|
||||
if (!i)
|
||||
{
|
||||
/* Create a new equivalence class in this bucket. */
|
||||
i = eqs_index++;
|
||||
if (i == eqs_alloc)
|
||||
eqs = (struct equivclass *)
|
||||
xrealloc (eqs, (eqs_alloc*=2) * sizeof(*eqs));
|
||||
eqs[i].next = *bucket;
|
||||
eqs[i].hash = h;
|
||||
eqs[i].line = ip;
|
||||
eqs[i].length = length;
|
||||
*bucket = i;
|
||||
break;
|
||||
}
|
||||
else if (eqs[i].hash == h)
|
||||
{
|
||||
char const *eqline = eqs[i].line;
|
||||
|
||||
/* Reuse existing equivalence class if the lines are identical.
|
||||
This detects the common case of exact identity
|
||||
faster than complete comparison would. */
|
||||
if (eqs[i].length == length && memcmp (eqline, ip, length) == 0)
|
||||
break;
|
||||
|
||||
/* Reuse existing class if line_cmp reports the lines equal. */
|
||||
if (use_line_cmp && line_cmp (eqline, ip) == 0)
|
||||
break;
|
||||
}
|
||||
|
||||
/* Maybe increase the size of the line table. */
|
||||
if (line == alloc_lines)
|
||||
{
|
||||
/* Double (alloc_lines - linbuf_base) by adding to alloc_lines. */
|
||||
alloc_lines = 2 * alloc_lines - linbuf_base;
|
||||
cureqs = (int *) xrealloc (cureqs, alloc_lines * sizeof (*cureqs));
|
||||
linbuf = (char const **) xrealloc (linbuf + linbuf_base,
|
||||
(alloc_lines - linbuf_base)
|
||||
* sizeof (*linbuf))
|
||||
- linbuf_base;
|
||||
}
|
||||
linbuf[line] = ip;
|
||||
cureqs[line] = i;
|
||||
++line;
|
||||
}
|
||||
|
||||
current->buffered_lines = line;
|
||||
|
||||
for (i = 0; ; i++)
|
||||
{
|
||||
/* Record the line start for lines in the suffix that we care about.
|
||||
Record one more line start than lines,
|
||||
so that we can compute the length of any buffered line. */
|
||||
if (line == alloc_lines)
|
||||
{
|
||||
/* Double (alloc_lines - linbuf_base) by adding to alloc_lines. */
|
||||
alloc_lines = 2 * alloc_lines - linbuf_base;
|
||||
linbuf = (char const **) xrealloc (linbuf + linbuf_base,
|
||||
(alloc_lines - linbuf_base)
|
||||
* sizeof (*linbuf))
|
||||
- linbuf_base;
|
||||
}
|
||||
linbuf[line] = (char const *) p;
|
||||
|
||||
if ((char const *) p == bufend)
|
||||
break;
|
||||
|
||||
if (context <= i && no_diff_means_no_output)
|
||||
break;
|
||||
|
||||
line++;
|
||||
|
||||
while (*p++ != '\n')
|
||||
;
|
||||
}
|
||||
|
||||
/* Done with cache in local variables. */
|
||||
current->linbuf = linbuf;
|
||||
current->valid_lines = line;
|
||||
current->alloc_lines = alloc_lines;
|
||||
current->equivs = cureqs;
|
||||
equivs = eqs;
|
||||
equivs_alloc = eqs_alloc;
|
||||
equivs_index = eqs_index;
|
||||
}
|
||||
|
||||
/* Prepare the end of the text. Make sure it's initialized.
|
||||
Make sure text ends in a newline,
|
||||
but remember that we had to add one. */
|
||||
|
||||
static void
|
||||
prepare_text_end (current)
|
||||
struct file_data *current;
|
||||
{
|
||||
size_t buffered_chars = current->buffered_chars;
|
||||
char *p = current->buffer;
|
||||
|
||||
if (buffered_chars == 0 || p[buffered_chars - 1] == '\n')
|
||||
current->missing_newline = 0;
|
||||
else
|
||||
{
|
||||
p[buffered_chars++] = '\n';
|
||||
current->buffered_chars = buffered_chars;
|
||||
current->missing_newline = 1;
|
||||
}
|
||||
|
||||
/* Don't use uninitialized storage when planting or using sentinels. */
|
||||
if (p)
|
||||
bzero (p + buffered_chars, sizeof (word));
|
||||
}
|
||||
|
||||
/* Given a vector of two file_data objects, find the identical
|
||||
prefixes and suffixes of each object. */
|
||||
|
||||
static void
|
||||
find_identical_ends (filevec)
|
||||
struct file_data filevec[];
|
||||
{
|
||||
word *w0, *w1;
|
||||
char *p0, *p1, *buffer0, *buffer1;
|
||||
char const *end0, *beg0;
|
||||
char const **linbuf0, **linbuf1;
|
||||
int i, lines;
|
||||
size_t n0, n1, tem;
|
||||
int alloc_lines0, alloc_lines1;
|
||||
int buffered_prefix, prefix_count, prefix_mask;
|
||||
|
||||
slurp (&filevec[0]);
|
||||
if (filevec[0].desc != filevec[1].desc)
|
||||
slurp (&filevec[1]);
|
||||
else
|
||||
{
|
||||
filevec[1].buffer = filevec[0].buffer;
|
||||
filevec[1].bufsize = filevec[0].bufsize;
|
||||
filevec[1].buffered_chars = filevec[0].buffered_chars;
|
||||
}
|
||||
for (i = 0; i < 2; i++)
|
||||
prepare_text_end (&filevec[i]);
|
||||
|
||||
/* Find identical prefix. */
|
||||
|
||||
p0 = buffer0 = filevec[0].buffer;
|
||||
p1 = buffer1 = filevec[1].buffer;
|
||||
|
||||
n0 = filevec[0].buffered_chars;
|
||||
n1 = filevec[1].buffered_chars;
|
||||
|
||||
if (p0 == p1)
|
||||
/* The buffers are the same; sentinels won't work. */
|
||||
p0 = p1 += n1;
|
||||
else
|
||||
{
|
||||
/* Insert end sentinels, in this case characters that are guaranteed
|
||||
to make the equality test false, and thus terminate the loop. */
|
||||
|
||||
if (n0 < n1)
|
||||
p0[n0] = ~p1[n0];
|
||||
else
|
||||
p1[n1] = ~p0[n1];
|
||||
|
||||
/* Loop until first mismatch, or to the sentinel characters. */
|
||||
|
||||
/* Compare a word at a time for speed. */
|
||||
w0 = (word *) p0;
|
||||
w1 = (word *) p1;
|
||||
while (*w0++ == *w1++)
|
||||
;
|
||||
--w0, --w1;
|
||||
|
||||
/* Do the last few bytes of comparison a byte at a time. */
|
||||
p0 = (char *) w0;
|
||||
p1 = (char *) w1;
|
||||
while (*p0++ == *p1++)
|
||||
;
|
||||
--p0, --p1;
|
||||
|
||||
/* Don't mistakenly count missing newline as part of prefix. */
|
||||
if (ROBUST_OUTPUT_STYLE (output_style)
|
||||
&& (buffer0 + n0 - filevec[0].missing_newline < p0)
|
||||
!=
|
||||
(buffer1 + n1 - filevec[1].missing_newline < p1))
|
||||
--p0, --p1;
|
||||
}
|
||||
|
||||
/* Now P0 and P1 point at the first nonmatching characters. */
|
||||
|
||||
/* Skip back to last line-beginning in the prefix,
|
||||
and then discard up to HORIZON_LINES lines from the prefix. */
|
||||
i = horizon_lines;
|
||||
while (p0 != buffer0 && (p0[-1] != '\n' || i--))
|
||||
--p0, --p1;
|
||||
|
||||
/* Record the prefix. */
|
||||
filevec[0].prefix_end = p0;
|
||||
filevec[1].prefix_end = p1;
|
||||
|
||||
/* Find identical suffix. */
|
||||
|
||||
/* P0 and P1 point beyond the last chars not yet compared. */
|
||||
p0 = buffer0 + n0;
|
||||
p1 = buffer1 + n1;
|
||||
|
||||
if (! ROBUST_OUTPUT_STYLE (output_style)
|
||||
|| filevec[0].missing_newline == filevec[1].missing_newline)
|
||||
{
|
||||
end0 = p0; /* Addr of last char in file 0. */
|
||||
|
||||
/* Get value of P0 at which we should stop scanning backward:
|
||||
this is when either P0 or P1 points just past the last char
|
||||
of the identical prefix. */
|
||||
beg0 = filevec[0].prefix_end + (n0 < n1 ? 0 : n0 - n1);
|
||||
|
||||
/* Scan back until chars don't match or we reach that point. */
|
||||
while (p0 != beg0)
|
||||
if (*--p0 != *--p1)
|
||||
{
|
||||
/* Point at the first char of the matching suffix. */
|
||||
++p0, ++p1;
|
||||
beg0 = p0;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Are we at a line-beginning in both files? If not, add the rest of
|
||||
this line to the main body. Discard up to HORIZON_LINES lines from
|
||||
the identical suffix. Also, discard one extra line,
|
||||
because shift_boundaries may need it. */
|
||||
i = horizon_lines + !((buffer0 == p0 || p0[-1] == '\n')
|
||||
&&
|
||||
(buffer1 == p1 || p1[-1] == '\n'));
|
||||
while (i-- && p0 != end0)
|
||||
while (*p0++ != '\n')
|
||||
;
|
||||
|
||||
p1 += p0 - beg0;
|
||||
}
|
||||
|
||||
/* Record the suffix. */
|
||||
filevec[0].suffix_begin = p0;
|
||||
filevec[1].suffix_begin = p1;
|
||||
|
||||
/* Calculate number of lines of prefix to save.
|
||||
|
||||
prefix_count == 0 means save the whole prefix;
|
||||
we need this with for options like -D that output the whole file.
|
||||
We also need it for options like -F that output some preceding line;
|
||||
at least we will need to find the last few lines,
|
||||
but since we don't know how many, it's easiest to find them all.
|
||||
|
||||
Otherwise, prefix_count != 0. Save just prefix_count lines at start
|
||||
of the line buffer; they'll be moved to the proper location later.
|
||||
Handle 1 more line than the context says (because we count 1 too many),
|
||||
rounded up to the next power of 2 to speed index computation. */
|
||||
|
||||
if (no_diff_means_no_output && ! function_regexp_list)
|
||||
{
|
||||
for (prefix_count = 1; prefix_count < context + 1; prefix_count *= 2)
|
||||
;
|
||||
prefix_mask = prefix_count - 1;
|
||||
alloc_lines0
|
||||
= prefix_count
|
||||
+ GUESS_LINES (0, 0, p0 - filevec[0].prefix_end)
|
||||
+ context;
|
||||
}
|
||||
else
|
||||
{
|
||||
prefix_count = 0;
|
||||
prefix_mask = ~0;
|
||||
alloc_lines0 = GUESS_LINES (0, 0, n0);
|
||||
}
|
||||
|
||||
lines = 0;
|
||||
linbuf0 = (char const **) xmalloc (alloc_lines0 * sizeof (*linbuf0));
|
||||
|
||||
/* If the prefix is needed, find the prefix lines. */
|
||||
if (! (no_diff_means_no_output
|
||||
&& filevec[0].prefix_end == p0
|
||||
&& filevec[1].prefix_end == p1))
|
||||
{
|
||||
p0 = buffer0;
|
||||
end0 = filevec[0].prefix_end;
|
||||
while (p0 != end0)
|
||||
{
|
||||
int l = lines++ & prefix_mask;
|
||||
if (l == alloc_lines0)
|
||||
linbuf0 = (char const **) xrealloc (linbuf0, (alloc_lines0 *= 2)
|
||||
* sizeof(*linbuf0));
|
||||
linbuf0[l] = p0;
|
||||
while (*p0++ != '\n')
|
||||
;
|
||||
}
|
||||
}
|
||||
buffered_prefix = prefix_count && context < lines ? context : lines;
|
||||
|
||||
/* Allocate line buffer 1. */
|
||||
tem = prefix_count ? filevec[1].suffix_begin - buffer1 : n1;
|
||||
|
||||
alloc_lines1
|
||||
= (buffered_prefix
|
||||
+ GUESS_LINES (lines, filevec[1].prefix_end - buffer1, tem)
|
||||
+ context);
|
||||
linbuf1 = (char const **) xmalloc (alloc_lines1 * sizeof (*linbuf1));
|
||||
|
||||
if (buffered_prefix != lines)
|
||||
{
|
||||
/* Rotate prefix lines to proper location. */
|
||||
for (i = 0; i < buffered_prefix; i++)
|
||||
linbuf1[i] = linbuf0[(lines - context + i) & prefix_mask];
|
||||
for (i = 0; i < buffered_prefix; i++)
|
||||
linbuf0[i] = linbuf1[i];
|
||||
}
|
||||
|
||||
/* Initialize line buffer 1 from line buffer 0. */
|
||||
for (i = 0; i < buffered_prefix; i++)
|
||||
linbuf1[i] = linbuf0[i] - buffer0 + buffer1;
|
||||
|
||||
/* Record the line buffer, adjusted so that
|
||||
linbuf*[0] points at the first differing line. */
|
||||
filevec[0].linbuf = linbuf0 + buffered_prefix;
|
||||
filevec[1].linbuf = linbuf1 + buffered_prefix;
|
||||
filevec[0].linbuf_base = filevec[1].linbuf_base = - buffered_prefix;
|
||||
filevec[0].alloc_lines = alloc_lines0 - buffered_prefix;
|
||||
filevec[1].alloc_lines = alloc_lines1 - buffered_prefix;
|
||||
filevec[0].prefix_lines = filevec[1].prefix_lines = lines;
|
||||
}
|
||||
|
||||
/* Largest primes less than some power of two, for nbuckets. Values range
|
||||
from useful to preposterous. If one of these numbers isn't prime
|
||||
after all, don't blame it on me, blame it on primes (6) . . . */
|
||||
static int const primes[] =
|
||||
{
|
||||
509,
|
||||
1021,
|
||||
2039,
|
||||
4093,
|
||||
8191,
|
||||
16381,
|
||||
32749,
|
||||
#if 32767 < INT_MAX
|
||||
65521,
|
||||
131071,
|
||||
262139,
|
||||
524287,
|
||||
1048573,
|
||||
2097143,
|
||||
4194301,
|
||||
8388593,
|
||||
16777213,
|
||||
33554393,
|
||||
67108859, /* Preposterously large . . . */
|
||||
134217689,
|
||||
268435399,
|
||||
536870909,
|
||||
1073741789,
|
||||
2147483647,
|
||||
#endif
|
||||
0
|
||||
};
|
||||
|
||||
/* Given a vector of two file_data objects, read the file associated
|
||||
with each one, and build the table of equivalence classes.
|
||||
Return 1 if either file appears to be a binary file.
|
||||
If PRETEND_BINARY is nonzero, pretend they are binary regardless. */
|
||||
|
||||
int
|
||||
read_files (filevec, pretend_binary)
|
||||
struct file_data filevec[];
|
||||
int pretend_binary;
|
||||
{
|
||||
int i;
|
||||
int skip_test = always_text_flag | pretend_binary;
|
||||
int appears_binary = pretend_binary | sip (&filevec[0], skip_test);
|
||||
|
||||
if (filevec[0].desc != filevec[1].desc)
|
||||
appears_binary |= sip (&filevec[1], skip_test | appears_binary);
|
||||
else
|
||||
{
|
||||
filevec[1].buffer = filevec[0].buffer;
|
||||
filevec[1].bufsize = filevec[0].bufsize;
|
||||
filevec[1].buffered_chars = filevec[0].buffered_chars;
|
||||
}
|
||||
if (appears_binary)
|
||||
{
|
||||
#if HAVE_SETMODE
|
||||
setmode (filevec[0].desc, O_BINARY);
|
||||
setmode (filevec[1].desc, O_BINARY);
|
||||
#endif
|
||||
return 1;
|
||||
}
|
||||
|
||||
find_identical_ends (filevec);
|
||||
|
||||
equivs_alloc = filevec[0].alloc_lines + filevec[1].alloc_lines + 1;
|
||||
equivs = (struct equivclass *) xmalloc (equivs_alloc * sizeof (struct equivclass));
|
||||
/* Equivalence class 0 is permanently safe for lines that were not
|
||||
hashed. Real equivalence classes start at 1. */
|
||||
equivs_index = 1;
|
||||
|
||||
for (i = 0; primes[i] < equivs_alloc / 3; i++)
|
||||
if (! primes[i])
|
||||
abort ();
|
||||
nbuckets = primes[i];
|
||||
|
||||
buckets = (int *) xmalloc ((nbuckets + 1) * sizeof (*buckets));
|
||||
bzero (buckets++, (nbuckets + 1) * sizeof (*buckets));
|
||||
|
||||
for (i = 0; i < 2; i++)
|
||||
find_and_hash_each_line (&filevec[i]);
|
||||
|
||||
filevec[0].equiv_max = filevec[1].equiv_max = equivs_index;
|
||||
|
||||
free (equivs);
|
||||
free (buckets - 1);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -1,71 +0,0 @@
|
||||
/* Normal-format output routines for GNU DIFF.
|
||||
Copyright (C) 1988, 1989, 1993 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
static void print_normal_hunk PARAMS((struct change *));
|
||||
|
||||
/* Print the edit-script SCRIPT as a normal diff.
|
||||
INF points to an array of descriptions of the two files. */
|
||||
|
||||
void
|
||||
print_normal_script (script)
|
||||
struct change *script;
|
||||
{
|
||||
print_script (script, find_change, print_normal_hunk);
|
||||
}
|
||||
|
||||
/* Print a hunk of a normal diff.
|
||||
This is a contiguous portion of a complete edit script,
|
||||
describing changes in consecutive lines. */
|
||||
|
||||
static void
|
||||
print_normal_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int first0, last0, first1, last1, deletes, inserts;
|
||||
register int i;
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
analyze_hunk (hunk, &first0, &last0, &first1, &last1, &deletes, &inserts);
|
||||
if (!deletes && !inserts)
|
||||
return;
|
||||
|
||||
begin_output ();
|
||||
|
||||
/* Print out the line number header for this hunk */
|
||||
print_number_range (',', &files[0], first0, last0);
|
||||
fprintf (outfile, "%c", change_letter (inserts, deletes));
|
||||
print_number_range (',', &files[1], first1, last1);
|
||||
fprintf (outfile, "\n");
|
||||
|
||||
/* Print the lines that the first file has. */
|
||||
if (deletes)
|
||||
for (i = first0; i <= last0; i++)
|
||||
print_1_line ("<", &files[0].linbuf[i]);
|
||||
|
||||
if (inserts && deletes)
|
||||
fprintf (outfile, "---\n");
|
||||
|
||||
/* Print the lines that the second file has. */
|
||||
if (inserts)
|
||||
for (i = first1; i <= last1; i++)
|
||||
print_1_line (">", &files[1].linbuf[i]);
|
||||
}
|
||||
@@ -1,284 +0,0 @@
|
||||
/* sdiff-format output routines for GNU DIFF.
|
||||
Copyright (C) 1991, 1992, 1993 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY. No author or distributor
|
||||
accepts responsibility to anyone for the consequences of using it
|
||||
or for whether it serves any particular purpose or works at all,
|
||||
unless he says so in writing. Refer to the GNU DIFF General Public
|
||||
License for full details.
|
||||
|
||||
Everyone is granted permission to copy, modify and redistribute
|
||||
GNU DIFF, but only under the conditions described in the
|
||||
GNU DIFF General Public License. A copy of this license is
|
||||
supposed to have been given to you along with GNU DIFF so you
|
||||
can know your rights and responsibilities. It should be in a
|
||||
file named COPYING. Among other things, the copyright notice
|
||||
and this notice must be preserved on all copies. */
|
||||
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
static unsigned print_half_line PARAMS((char const * const *, unsigned, unsigned));
|
||||
static unsigned tab_from_to PARAMS((unsigned, unsigned));
|
||||
static void print_1sdiff_line PARAMS((char const * const *, int, char const * const *));
|
||||
static void print_sdiff_common_lines PARAMS((int, int));
|
||||
static void print_sdiff_hunk PARAMS((struct change *));
|
||||
|
||||
/* Next line number to be printed in the two input files. */
|
||||
static int next0, next1;
|
||||
|
||||
/* Print the edit-script SCRIPT as a sdiff style output. */
|
||||
|
||||
void
|
||||
print_sdiff_script (script)
|
||||
struct change *script;
|
||||
{
|
||||
begin_output ();
|
||||
|
||||
next0 = next1 = - files[0].prefix_lines;
|
||||
print_script (script, find_change, print_sdiff_hunk);
|
||||
|
||||
print_sdiff_common_lines (files[0].valid_lines, files[1].valid_lines);
|
||||
}
|
||||
|
||||
/* Tab from column FROM to column TO, where FROM <= TO. Yield TO. */
|
||||
|
||||
static unsigned
|
||||
tab_from_to (from, to)
|
||||
unsigned from, to;
|
||||
{
|
||||
FILE *out = outfile;
|
||||
unsigned tab;
|
||||
|
||||
if (! tab_expand_flag)
|
||||
for (tab = from + TAB_WIDTH - from % TAB_WIDTH; tab <= to; tab += TAB_WIDTH)
|
||||
{
|
||||
putc ('\t', out);
|
||||
from = tab;
|
||||
}
|
||||
while (from++ < to)
|
||||
putc (' ', out);
|
||||
return to;
|
||||
}
|
||||
|
||||
/*
|
||||
* Print the text for half an sdiff line. This means truncate to width
|
||||
* observing tabs, and trim a trailing newline. Returns the last column
|
||||
* written (not the number of chars).
|
||||
*/
|
||||
static unsigned
|
||||
print_half_line (line, indent, out_bound)
|
||||
char const * const *line;
|
||||
unsigned indent, out_bound;
|
||||
{
|
||||
FILE *out = outfile;
|
||||
register unsigned in_position = 0, out_position = 0;
|
||||
register char const
|
||||
*text_pointer = line[0],
|
||||
*text_limit = line[1];
|
||||
|
||||
while (text_pointer < text_limit)
|
||||
{
|
||||
register unsigned char c = *text_pointer++;
|
||||
|
||||
switch (c)
|
||||
{
|
||||
case '\t':
|
||||
{
|
||||
unsigned spaces = TAB_WIDTH - in_position % TAB_WIDTH;
|
||||
if (in_position == out_position)
|
||||
{
|
||||
unsigned tabstop = out_position + spaces;
|
||||
if (tab_expand_flag)
|
||||
{
|
||||
if (out_bound < tabstop)
|
||||
tabstop = out_bound;
|
||||
for (; out_position < tabstop; out_position++)
|
||||
putc (' ', out);
|
||||
}
|
||||
else
|
||||
if (tabstop < out_bound)
|
||||
{
|
||||
out_position = tabstop;
|
||||
putc (c, out);
|
||||
}
|
||||
}
|
||||
in_position += spaces;
|
||||
}
|
||||
break;
|
||||
|
||||
case '\r':
|
||||
{
|
||||
putc (c, out);
|
||||
tab_from_to (0, indent);
|
||||
in_position = out_position = 0;
|
||||
}
|
||||
break;
|
||||
|
||||
case '\b':
|
||||
if (in_position != 0 && --in_position < out_bound)
|
||||
if (out_position <= in_position)
|
||||
/* Add spaces to make up for suppressed tab past out_bound. */
|
||||
for (; out_position < in_position; out_position++)
|
||||
putc (' ', out);
|
||||
else
|
||||
{
|
||||
out_position = in_position;
|
||||
putc (c, out);
|
||||
}
|
||||
break;
|
||||
|
||||
case '\f':
|
||||
case '\v':
|
||||
control_char:
|
||||
if (in_position < out_bound)
|
||||
putc (c, out);
|
||||
break;
|
||||
|
||||
default:
|
||||
if (! ISPRINT (c))
|
||||
goto control_char;
|
||||
/* falls through */
|
||||
case ' ':
|
||||
if (in_position++ < out_bound)
|
||||
{
|
||||
out_position = in_position;
|
||||
putc (c, out);
|
||||
}
|
||||
break;
|
||||
|
||||
case '\n':
|
||||
return out_position;
|
||||
}
|
||||
}
|
||||
|
||||
return out_position;
|
||||
}
|
||||
|
||||
/*
|
||||
* Print side by side lines with a separator in the middle.
|
||||
* 0 parameters are taken to indicate white space text.
|
||||
* Blank lines that can easily be caught are reduced to a single newline.
|
||||
*/
|
||||
|
||||
static void
|
||||
print_1sdiff_line (left, sep, right)
|
||||
char const * const *left;
|
||||
int sep;
|
||||
char const * const *right;
|
||||
{
|
||||
FILE *out = outfile;
|
||||
unsigned hw = sdiff_half_width, c2o = sdiff_column2_offset;
|
||||
unsigned col = 0;
|
||||
int put_newline = 0;
|
||||
|
||||
if (left)
|
||||
{
|
||||
if (left[1][-1] == '\n')
|
||||
put_newline = 1;
|
||||
col = print_half_line (left, 0, hw);
|
||||
}
|
||||
|
||||
if (sep != ' ')
|
||||
{
|
||||
col = tab_from_to (col, (hw + c2o - 1) / 2) + 1;
|
||||
if (sep == '|' && put_newline != (right[1][-1] == '\n'))
|
||||
sep = put_newline ? '/' : '\\';
|
||||
putc (sep, out);
|
||||
}
|
||||
|
||||
if (right)
|
||||
{
|
||||
if (right[1][-1] == '\n')
|
||||
put_newline = 1;
|
||||
if (**right != '\n')
|
||||
{
|
||||
col = tab_from_to (col, c2o);
|
||||
print_half_line (right, col, hw);
|
||||
}
|
||||
}
|
||||
|
||||
if (put_newline)
|
||||
putc ('\n', out);
|
||||
}
|
||||
|
||||
/* Print lines common to both files in side-by-side format. */
|
||||
static void
|
||||
print_sdiff_common_lines (limit0, limit1)
|
||||
int limit0, limit1;
|
||||
{
|
||||
int i0 = next0, i1 = next1;
|
||||
|
||||
if (! sdiff_skip_common_lines && (i0 != limit0 || i1 != limit1))
|
||||
{
|
||||
if (sdiff_help_sdiff)
|
||||
fprintf (outfile, "i%d,%d\n", limit0 - i0, limit1 - i1);
|
||||
|
||||
if (! sdiff_left_only)
|
||||
{
|
||||
while (i0 != limit0 && i1 != limit1)
|
||||
print_1sdiff_line (&files[0].linbuf[i0++], ' ', &files[1].linbuf[i1++]);
|
||||
while (i1 != limit1)
|
||||
print_1sdiff_line (0, ')', &files[1].linbuf[i1++]);
|
||||
}
|
||||
while (i0 != limit0)
|
||||
print_1sdiff_line (&files[0].linbuf[i0++], '(', 0);
|
||||
}
|
||||
|
||||
next0 = limit0;
|
||||
next1 = limit1;
|
||||
}
|
||||
|
||||
/* Print a hunk of an sdiff diff.
|
||||
This is a contiguous portion of a complete edit script,
|
||||
describing changes in consecutive lines. */
|
||||
|
||||
static void
|
||||
print_sdiff_hunk (hunk)
|
||||
struct change *hunk;
|
||||
{
|
||||
int first0, last0, first1, last1, deletes, inserts;
|
||||
register int i, j;
|
||||
|
||||
/* Determine range of line numbers involved in each file. */
|
||||
analyze_hunk (hunk, &first0, &last0, &first1, &last1, &deletes, &inserts);
|
||||
if (!deletes && !inserts)
|
||||
return;
|
||||
|
||||
/* Print out lines up to this change. */
|
||||
print_sdiff_common_lines (first0, first1);
|
||||
|
||||
if (sdiff_help_sdiff)
|
||||
fprintf (outfile, "c%d,%d\n", last0 - first0 + 1, last1 - first1 + 1);
|
||||
|
||||
/* Print ``xxx | xxx '' lines */
|
||||
if (inserts && deletes)
|
||||
{
|
||||
for (i = first0, j = first1; i <= last0 && j <= last1; ++i, ++j)
|
||||
print_1sdiff_line (&files[0].linbuf[i], '|', &files[1].linbuf[j]);
|
||||
deletes = i <= last0;
|
||||
inserts = j <= last1;
|
||||
next0 = first0 = i;
|
||||
next1 = first1 = j;
|
||||
}
|
||||
|
||||
|
||||
/* Print `` > xxx '' lines */
|
||||
if (inserts)
|
||||
{
|
||||
for (j = first1; j <= last1; ++j)
|
||||
print_1sdiff_line (0, '>', &files[1].linbuf[j]);
|
||||
next1 = j;
|
||||
}
|
||||
|
||||
/* Print ``xxx < '' lines */
|
||||
if (deletes)
|
||||
{
|
||||
for (i = first0; i <= last0; ++i)
|
||||
print_1sdiff_line (&files[0].linbuf[i], '<', 0);
|
||||
next0 = i;
|
||||
}
|
||||
}
|
||||
@@ -1,270 +0,0 @@
|
||||
/* System dependent declarations.
|
||||
Copyright (C) 1988, 1989, 1992, 1993, 1994 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
/* We must define `volatile' and `const' first (the latter inside config.h),
|
||||
so that they're used consistently in all system includes. */
|
||||
#if !__STDC__
|
||||
#ifndef volatile
|
||||
#define volatile
|
||||
#endif
|
||||
#endif
|
||||
#include <config.h>
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#if __STDC__
|
||||
#define PARAMS(args) args
|
||||
#define VOID void
|
||||
#else
|
||||
#define PARAMS(args) ()
|
||||
#define VOID char
|
||||
#endif
|
||||
|
||||
#if STAT_MACROS_BROKEN
|
||||
#undef S_ISBLK
|
||||
#undef S_ISCHR
|
||||
#undef S_ISDIR
|
||||
#undef S_ISFIFO
|
||||
#undef S_ISREG
|
||||
#undef S_ISSOCK
|
||||
#endif
|
||||
#ifndef S_ISDIR
|
||||
#define S_ISDIR(mode) (((mode) & S_IFMT) == S_IFDIR)
|
||||
#endif
|
||||
#ifndef S_ISREG
|
||||
#define S_ISREG(mode) (((mode) & S_IFMT) == S_IFREG)
|
||||
#endif
|
||||
#if !defined(S_ISBLK) && defined(S_IFBLK)
|
||||
#define S_ISBLK(mode) (((mode) & S_IFMT) == S_IFBLK)
|
||||
#endif
|
||||
#if !defined(S_ISCHR) && defined(S_IFCHR)
|
||||
#define S_ISCHR(mode) (((mode) & S_IFMT) == S_IFCHR)
|
||||
#endif
|
||||
#if !defined(S_ISFIFO) && defined(S_IFFIFO)
|
||||
#define S_ISFIFO(mode) (((mode) & S_IFMT) == S_IFFIFO)
|
||||
#endif
|
||||
#if !defined(S_ISSOCK) && defined(S_IFSOCK)
|
||||
#define S_ISSOCK(mode) (((mode) & S_IFMT) == S_IFSOCK)
|
||||
#endif
|
||||
|
||||
#if HAVE_UNISTD_H
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
|
||||
#ifndef SEEK_SET
|
||||
#define SEEK_SET 0
|
||||
#endif
|
||||
#ifndef SEEK_CUR
|
||||
#define SEEK_CUR 1
|
||||
#endif
|
||||
|
||||
#ifndef STDIN_FILENO
|
||||
#define STDIN_FILENO 0
|
||||
#endif
|
||||
#ifndef STDOUT_FILENO
|
||||
#define STDOUT_FILENO 1
|
||||
#endif
|
||||
#ifndef STDERR_FILENO
|
||||
#define STDERR_FILENO 2
|
||||
#endif
|
||||
|
||||
/* I believe that all relevant systems have
|
||||
time.h. It is in ANSI, for example. The
|
||||
code below looks quite bogus as I don't think
|
||||
sys/time.h is ever a substitute for time.h;
|
||||
it is something different. */
|
||||
#define HAVE_TIME_H 1
|
||||
|
||||
#if HAVE_TIME_H
|
||||
#include <time.h>
|
||||
#else
|
||||
#include <sys/time.h>
|
||||
#endif
|
||||
|
||||
#if HAVE_FCNTL_H
|
||||
#include <fcntl.h>
|
||||
#else
|
||||
#if HAVE_SYS_FILE_H
|
||||
#include <sys/file.h>
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef O_RDONLY
|
||||
#define O_RDONLY 0
|
||||
#endif
|
||||
|
||||
#if HAVE_SYS_WAIT_H
|
||||
#include <sys/wait.h>
|
||||
#endif
|
||||
#ifndef WEXITSTATUS
|
||||
#define WEXITSTATUS(stat_val) ((unsigned) (stat_val) >> 8)
|
||||
#endif
|
||||
#ifndef WIFEXITED
|
||||
#define WIFEXITED(stat_val) (((stat_val) & 255) == 0)
|
||||
#endif
|
||||
|
||||
#ifndef STAT_BLOCKSIZE
|
||||
#if HAVE_ST_BLKSIZE
|
||||
#define STAT_BLOCKSIZE(s) (s).st_blksize
|
||||
#else
|
||||
#define STAT_BLOCKSIZE(s) (8 * 1024)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if HAVE_DIRENT_H
|
||||
# include <dirent.h>
|
||||
# define NAMLEN(dirent) strlen((dirent)->d_name)
|
||||
#else
|
||||
# define dirent direct
|
||||
# define NAMLEN(dirent) ((dirent)->d_namlen)
|
||||
# if HAVE_SYS_NDIR_H
|
||||
# include <sys/ndir.h>
|
||||
# endif
|
||||
# if HAVE_SYS_DIR_H
|
||||
# include <sys/dir.h>
|
||||
# endif
|
||||
# if HAVE_NDIR_H
|
||||
# include <ndir.h>
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if HAVE_VFORK_H
|
||||
#include <vfork.h>
|
||||
#endif
|
||||
|
||||
#if HAVE_STDLIB_H || defined(STDC_HEADERS)
|
||||
#include <stdlib.h>
|
||||
#else
|
||||
VOID *malloc ();
|
||||
VOID *realloc ();
|
||||
#endif
|
||||
#ifndef getenv
|
||||
char *getenv ();
|
||||
#endif
|
||||
|
||||
#if HAVE_LIMITS_H
|
||||
#include <limits.h>
|
||||
#endif
|
||||
#ifndef INT_MAX
|
||||
#define INT_MAX 2147483647
|
||||
#endif
|
||||
#ifndef CHAR_BIT
|
||||
#define CHAR_BIT 8
|
||||
#endif
|
||||
|
||||
#if STDC_HEADERS || HAVE_STRING_H
|
||||
# include <string.h>
|
||||
# ifndef bzero
|
||||
# define bzero(s, n) memset (s, 0, n)
|
||||
# endif
|
||||
#else
|
||||
# if !HAVE_STRCHR
|
||||
# define strchr index
|
||||
# define strrchr rindex
|
||||
# endif
|
||||
char *strchr (), *strrchr ();
|
||||
# if !HAVE_MEMCHR
|
||||
# define memcmp(s1, s2, n) bcmp (s1, s2, n)
|
||||
# define memcpy(d, s, n) bcopy (s, d, n)
|
||||
void *memchr ();
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#include <ctype.h>
|
||||
/* CTYPE_DOMAIN (C) is nonzero if the unsigned char C can safely be given
|
||||
as an argument to <ctype.h> macros like `isspace'. */
|
||||
#if STDC_HEADERS
|
||||
#define CTYPE_DOMAIN(c) 1
|
||||
#else
|
||||
#define CTYPE_DOMAIN(c) ((unsigned) (c) <= 0177)
|
||||
#endif
|
||||
#ifndef ISPRINT
|
||||
#define ISPRINT(c) (CTYPE_DOMAIN (c) && isprint (c))
|
||||
#endif
|
||||
#ifndef ISSPACE
|
||||
#define ISSPACE(c) (CTYPE_DOMAIN (c) && isspace (c))
|
||||
#endif
|
||||
#ifndef ISUPPER
|
||||
#define ISUPPER(c) (CTYPE_DOMAIN (c) && isupper (c))
|
||||
#endif
|
||||
|
||||
#ifndef ISDIGIT
|
||||
#define ISDIGIT(c) ((unsigned) (c) - '0' <= 9)
|
||||
#endif
|
||||
|
||||
#include <errno.h>
|
||||
#if !STDC_HEADERS
|
||||
extern int errno;
|
||||
#endif
|
||||
|
||||
#ifdef min
|
||||
#undef min
|
||||
#endif
|
||||
#ifdef max
|
||||
#undef max
|
||||
#endif
|
||||
#define min(a,b) ((a) <= (b) ? (a) : (b))
|
||||
#define max(a,b) ((a) >= (b) ? (a) : (b))
|
||||
|
||||
/* This section contains Posix-compliant defaults for macros
|
||||
that are meant to be overridden by hand in config.h as needed. */
|
||||
|
||||
#ifndef filename_cmp
|
||||
#define filename_cmp(a, b) strcmp (a, b)
|
||||
#endif
|
||||
|
||||
#ifndef filename_lastdirchar
|
||||
#define filename_lastdirchar(filename) strrchr (filename, '/')
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_FORK
|
||||
#define HAVE_FORK 1
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_SETMODE
|
||||
#define HAVE_SETMODE 0
|
||||
#endif
|
||||
|
||||
#ifndef initialize_main
|
||||
#define initialize_main(argcp, argvp)
|
||||
#endif
|
||||
|
||||
/* Do struct stat *S, *T describe the same file? Answer -1 if unknown. */
|
||||
#ifndef same_file
|
||||
#define same_file(s,t) ((s)->st_ino==(t)->st_ino && (s)->st_dev==(t)->st_dev)
|
||||
#endif
|
||||
|
||||
/* Place into Q a quoted version of A suitable for `popen' or `system',
|
||||
incrementing Q and junking A.
|
||||
Do not increment Q by more than 4 * strlen (A) + 2. */
|
||||
#ifndef SYSTEM_QUOTE_ARG
|
||||
#define SYSTEM_QUOTE_ARG(q, a) \
|
||||
{ \
|
||||
*(q)++ = '\''; \
|
||||
for (; *(a); *(q)++ = *(a)++) \
|
||||
if (*(a) == '\'') \
|
||||
{ \
|
||||
*(q)++ = '\''; \
|
||||
*(q)++ = '\\'; \
|
||||
*(q)++ = '\''; \
|
||||
} \
|
||||
*(q)++ = '\''; \
|
||||
}
|
||||
#endif
|
||||
@@ -1,722 +0,0 @@
|
||||
/* Support routines for GNU DIFF.
|
||||
Copyright (C) 1988, 1989, 1992, 1993, 1994, 1997 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU DIFF.
|
||||
|
||||
GNU DIFF is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU DIFF is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU DIFF; see the file COPYING. If not, write to
|
||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||
|
||||
#include "diff.h"
|
||||
|
||||
/* Queue up one-line messages to be printed at the end,
|
||||
when -l is specified. Each message is recorded with a `struct msg'. */
|
||||
|
||||
struct msg
|
||||
{
|
||||
struct msg *next;
|
||||
char const *format;
|
||||
char const *arg1;
|
||||
char const *arg2;
|
||||
char const *arg3;
|
||||
char const *arg4;
|
||||
};
|
||||
|
||||
/* Head of the chain of queues messages. */
|
||||
|
||||
static struct msg *msg_chain;
|
||||
|
||||
/* Tail of the chain of queues messages. */
|
||||
|
||||
static struct msg **msg_chain_end = &msg_chain;
|
||||
|
||||
/* Use when a system call returns non-zero status.
|
||||
TEXT should normally be the file name. */
|
||||
|
||||
void
|
||||
perror_with_name (text)
|
||||
char const *text;
|
||||
{
|
||||
int e = errno;
|
||||
fprintf (stderr, "%s: ", diff_program_name);
|
||||
errno = e;
|
||||
perror (text);
|
||||
}
|
||||
|
||||
/* Use when a system call returns non-zero status and that is fatal. */
|
||||
|
||||
void
|
||||
pfatal_with_name (text)
|
||||
char const *text;
|
||||
{
|
||||
int e = errno;
|
||||
print_message_queue ();
|
||||
fprintf (stderr, "%s: ", diff_program_name);
|
||||
errno = e;
|
||||
perror (text);
|
||||
DIFF_ABORT (2);
|
||||
}
|
||||
|
||||
/* Print an error message from the format-string FORMAT
|
||||
with args ARG1 and ARG2. */
|
||||
|
||||
void
|
||||
diff_error (format, arg, arg1)
|
||||
char const *format, *arg, *arg1;
|
||||
{
|
||||
fprintf (stderr, "%s: ", diff_program_name);
|
||||
fprintf (stderr, format, arg, arg1);
|
||||
fprintf (stderr, "\n");
|
||||
}
|
||||
|
||||
/* Print an error message containing the string TEXT, then exit. */
|
||||
|
||||
void
|
||||
fatal (m)
|
||||
char const *m;
|
||||
{
|
||||
print_message_queue ();
|
||||
diff_error ("%s", m, 0);
|
||||
DIFF_ABORT (2);
|
||||
}
|
||||
|
||||
/* Like printf, except if -l in effect then save the message and print later.
|
||||
This is used for things like "binary files differ" and "Only in ...". */
|
||||
|
||||
void
|
||||
message (format, arg1, arg2)
|
||||
char const *format, *arg1, *arg2;
|
||||
{
|
||||
message5 (format, arg1, arg2, 0, 0);
|
||||
}
|
||||
|
||||
void
|
||||
message5 (format, arg1, arg2, arg3, arg4)
|
||||
char const *format, *arg1, *arg2, *arg3, *arg4;
|
||||
{
|
||||
if (paginate_flag)
|
||||
{
|
||||
struct msg *new = (struct msg *) xmalloc (sizeof (struct msg));
|
||||
new->format = format;
|
||||
new->arg1 = concat (arg1, "", "");
|
||||
new->arg2 = concat (arg2, "", "");
|
||||
new->arg3 = arg3 ? concat (arg3, "", "") : 0;
|
||||
new->arg4 = arg4 ? concat (arg4, "", "") : 0;
|
||||
new->next = 0;
|
||||
*msg_chain_end = new;
|
||||
msg_chain_end = &new->next;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (sdiff_help_sdiff)
|
||||
putc (' ', outfile);
|
||||
fprintf (outfile, format, arg1, arg2, arg3, arg4);
|
||||
}
|
||||
}
|
||||
|
||||
/* Output all the messages that were saved up by calls to `message'. */
|
||||
|
||||
void
|
||||
print_message_queue ()
|
||||
{
|
||||
struct msg *m;
|
||||
|
||||
for (m = msg_chain; m; m = m->next)
|
||||
fprintf (outfile, m->format, m->arg1, m->arg2, m->arg3, m->arg4);
|
||||
}
|
||||
|
||||
/* Call before outputting the results of comparing files NAME0 and NAME1
|
||||
to set up OUTFILE, the stdio stream for the output to go to.
|
||||
|
||||
Usually, OUTFILE is just stdout. But when -l was specified
|
||||
we fork off a `pr' and make OUTFILE a pipe to it.
|
||||
`pr' then outputs to our stdout. */
|
||||
|
||||
static char const *current_name0;
|
||||
static char const *current_name1;
|
||||
static int current_depth;
|
||||
|
||||
static int output_in_progress = 0;
|
||||
|
||||
void
|
||||
setup_output (name0, name1, depth)
|
||||
char const *name0, *name1;
|
||||
int depth;
|
||||
{
|
||||
current_name0 = name0;
|
||||
current_name1 = name1;
|
||||
current_depth = depth;
|
||||
}
|
||||
|
||||
#if HAVE_FORK && defined (PR_PROGRAM)
|
||||
static pid_t pr_pid;
|
||||
#endif
|
||||
|
||||
void
|
||||
begin_output ()
|
||||
{
|
||||
char *name;
|
||||
|
||||
if (output_in_progress)
|
||||
return;
|
||||
output_in_progress = 1;
|
||||
|
||||
/* Construct the header of this piece of diff. */
|
||||
name = xmalloc (strlen (current_name0) + strlen (current_name1)
|
||||
+ strlen (switch_string) + 7);
|
||||
/* Posix.2 section 4.17.6.1.1 specifies this format. But there is a
|
||||
bug in the first printing (IEEE Std 1003.2-1992 p 251 l 3304):
|
||||
it says that we must print only the last component of the pathnames.
|
||||
This requirement is silly and does not match historical practice. */
|
||||
sprintf (name, "diff%s %s %s", switch_string, current_name0, current_name1);
|
||||
|
||||
if (paginate_flag)
|
||||
{
|
||||
/* Make OUTFILE a pipe to a subsidiary `pr'. */
|
||||
|
||||
#ifdef PR_PROGRAM
|
||||
|
||||
# if HAVE_FORK
|
||||
int pipes[2];
|
||||
|
||||
if (pipe (pipes) != 0)
|
||||
pfatal_with_name ("pipe");
|
||||
|
||||
fflush (stdout);
|
||||
|
||||
pr_pid = vfork ();
|
||||
if (pr_pid < 0)
|
||||
pfatal_with_name ("vfork");
|
||||
|
||||
if (pr_pid == 0)
|
||||
{
|
||||
close (pipes[1]);
|
||||
if (pipes[0] != STDIN_FILENO)
|
||||
{
|
||||
if (dup2 (pipes[0], STDIN_FILENO) < 0)
|
||||
pfatal_with_name ("dup2");
|
||||
close (pipes[0]);
|
||||
}
|
||||
|
||||
execl (PR_PROGRAM, PR_PROGRAM, "-f", "-h", name, 0);
|
||||
pfatal_with_name (PR_PROGRAM);
|
||||
}
|
||||
else
|
||||
{
|
||||
close (pipes[0]);
|
||||
outfile = fdopen (pipes[1], "w");
|
||||
if (!outfile)
|
||||
pfatal_with_name ("fdopen");
|
||||
}
|
||||
# else /* ! HAVE_FORK */
|
||||
char *command = xmalloc (4 * strlen (name) + strlen (PR_PROGRAM) + 10);
|
||||
char *p;
|
||||
char const *a = name;
|
||||
sprintf (command, "%s -f -h ", PR_PROGRAM);
|
||||
p = command + strlen (command);
|
||||
SYSTEM_QUOTE_ARG (p, a);
|
||||
*p = 0;
|
||||
outfile = popen (command, "w");
|
||||
if (!outfile)
|
||||
pfatal_with_name (command);
|
||||
free (command);
|
||||
# endif /* ! HAVE_FORK */
|
||||
#else
|
||||
fatal ("This port does not support the --paginate option to diff.");
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
/* If -l was not specified, output the diff straight to `stdout'. */
|
||||
|
||||
/* If handling multiple files (because scanning a directory),
|
||||
print which files the following output is about. */
|
||||
if (current_depth > 0)
|
||||
fprintf (outfile, "%s\n", name);
|
||||
}
|
||||
|
||||
free (name);
|
||||
|
||||
/* A special header is needed at the beginning of context output. */
|
||||
switch (output_style)
|
||||
{
|
||||
case OUTPUT_CONTEXT:
|
||||
print_context_header (files, 0);
|
||||
break;
|
||||
|
||||
case OUTPUT_UNIFIED:
|
||||
print_context_header (files, 1);
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Call after the end of output of diffs for one file.
|
||||
If -l was given, close OUTFILE and get rid of the `pr' subfork. */
|
||||
|
||||
void
|
||||
finish_output ()
|
||||
{
|
||||
if (paginate_flag && outfile != 0 && outfile != stdout)
|
||||
{
|
||||
#ifdef PR_PROGRAM
|
||||
int wstatus;
|
||||
if (ferror (outfile))
|
||||
fatal ("write error");
|
||||
# if ! HAVE_FORK
|
||||
wstatus = pclose (outfile);
|
||||
# else /* HAVE_FORK */
|
||||
if (fclose (outfile) != 0)
|
||||
pfatal_with_name ("write error");
|
||||
if (waitpid (pr_pid, &wstatus, 0) < 0)
|
||||
pfatal_with_name ("waitpid");
|
||||
# endif /* HAVE_FORK */
|
||||
if (wstatus != 0)
|
||||
fatal ("subsidiary pr failed");
|
||||
#else
|
||||
fatal ("internal error in finish_output");
|
||||
#endif
|
||||
}
|
||||
|
||||
output_in_progress = 0;
|
||||
}
|
||||
|
||||
/* Compare two lines (typically one from each input file)
|
||||
according to the command line options.
|
||||
For efficiency, this is invoked only when the lines do not match exactly
|
||||
but an option like -i might cause us to ignore the difference.
|
||||
Return nonzero if the lines differ. */
|
||||
|
||||
int
|
||||
line_cmp (s1, s2)
|
||||
char const *s1, *s2;
|
||||
{
|
||||
register unsigned char const *t1 = (unsigned char const *) s1;
|
||||
register unsigned char const *t2 = (unsigned char const *) s2;
|
||||
|
||||
while (1)
|
||||
{
|
||||
register unsigned char c1 = *t1++;
|
||||
register unsigned char c2 = *t2++;
|
||||
|
||||
/* Test for exact char equality first, since it's a common case. */
|
||||
if (c1 != c2)
|
||||
{
|
||||
/* Ignore horizontal white space if -b or -w is specified. */
|
||||
|
||||
if (ignore_all_space_flag)
|
||||
{
|
||||
/* For -w, just skip past any white space. */
|
||||
while (ISSPACE (c1) && c1 != '\n') c1 = *t1++;
|
||||
while (ISSPACE (c2) && c2 != '\n') c2 = *t2++;
|
||||
}
|
||||
else if (ignore_space_change_flag)
|
||||
{
|
||||
/* For -b, advance past any sequence of white space in line 1
|
||||
and consider it just one Space, or nothing at all
|
||||
if it is at the end of the line. */
|
||||
if (ISSPACE (c1))
|
||||
{
|
||||
while (c1 != '\n')
|
||||
{
|
||||
c1 = *t1++;
|
||||
if (! ISSPACE (c1))
|
||||
{
|
||||
--t1;
|
||||
c1 = ' ';
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Likewise for line 2. */
|
||||
if (ISSPACE (c2))
|
||||
{
|
||||
while (c2 != '\n')
|
||||
{
|
||||
c2 = *t2++;
|
||||
if (! ISSPACE (c2))
|
||||
{
|
||||
--t2;
|
||||
c2 = ' ';
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (c1 != c2)
|
||||
{
|
||||
/* If we went too far when doing the simple test
|
||||
for equality, go back to the first non-white-space
|
||||
character in both sides and try again. */
|
||||
if (c2 == ' ' && c1 != '\n'
|
||||
&& (unsigned char const *) s1 + 1 < t1
|
||||
&& ISSPACE(t1[-2]))
|
||||
{
|
||||
--t1;
|
||||
continue;
|
||||
}
|
||||
if (c1 == ' ' && c2 != '\n'
|
||||
&& (unsigned char const *) s2 + 1 < t2
|
||||
&& ISSPACE(t2[-2]))
|
||||
{
|
||||
--t2;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Lowercase all letters if -i is specified. */
|
||||
|
||||
if (ignore_case_flag)
|
||||
{
|
||||
if (ISUPPER (c1))
|
||||
c1 = tolower (c1);
|
||||
if (ISUPPER (c2))
|
||||
c2 = tolower (c2);
|
||||
}
|
||||
|
||||
if (c1 != c2)
|
||||
break;
|
||||
}
|
||||
if (c1 == '\n')
|
||||
return 0;
|
||||
}
|
||||
|
||||
return (1);
|
||||
}
|
||||
|
||||
/* Find the consecutive changes at the start of the script START.
|
||||
Return the last link before the first gap. */
|
||||
|
||||
struct change *
|
||||
find_change (start)
|
||||
struct change *start;
|
||||
{
|
||||
return start;
|
||||
}
|
||||
|
||||
struct change *
|
||||
find_reverse_change (start)
|
||||
struct change *start;
|
||||
{
|
||||
return start;
|
||||
}
|
||||
|
||||
/* Divide SCRIPT into pieces by calling HUNKFUN and
|
||||
print each piece with PRINTFUN.
|
||||
Both functions take one arg, an edit script.
|
||||
|
||||
HUNKFUN is called with the tail of the script
|
||||
and returns the last link that belongs together with the start
|
||||
of the tail.
|
||||
|
||||
PRINTFUN takes a subscript which belongs together (with a null
|
||||
link at the end) and prints it. */
|
||||
|
||||
void
|
||||
print_script (script, hunkfun, printfun)
|
||||
struct change *script;
|
||||
struct change * (*hunkfun) PARAMS((struct change *));
|
||||
void (*printfun) PARAMS((struct change *));
|
||||
{
|
||||
struct change *next = script;
|
||||
|
||||
while (next)
|
||||
{
|
||||
struct change *this, *end;
|
||||
|
||||
/* Find a set of changes that belong together. */
|
||||
this = next;
|
||||
end = (*hunkfun) (next);
|
||||
|
||||
/* Disconnect them from the rest of the changes,
|
||||
making them a hunk, and remember the rest for next iteration. */
|
||||
next = end->link;
|
||||
end->link = 0;
|
||||
#ifdef DEBUG
|
||||
debug_script (this);
|
||||
#endif
|
||||
|
||||
/* Print this hunk. */
|
||||
(*printfun) (this);
|
||||
|
||||
/* Reconnect the script so it will all be freed properly. */
|
||||
end->link = next;
|
||||
}
|
||||
}
|
||||
|
||||
/* Print the text of a single line LINE,
|
||||
flagging it with the characters in LINE_FLAG (which say whether
|
||||
the line is inserted, deleted, changed, etc.). */
|
||||
|
||||
void
|
||||
print_1_line (line_flag, line)
|
||||
char const *line_flag;
|
||||
char const * const *line;
|
||||
{
|
||||
char const *text = line[0], *limit = line[1]; /* Help the compiler. */
|
||||
FILE *out = outfile; /* Help the compiler some more. */
|
||||
char const *flag_format = 0;
|
||||
|
||||
/* If -T was specified, use a Tab between the line-flag and the text.
|
||||
Otherwise use a Space (as Unix diff does).
|
||||
Print neither space nor tab if line-flags are empty. */
|
||||
|
||||
if (line_flag && *line_flag)
|
||||
{
|
||||
flag_format = tab_align_flag ? "%s\t" : "%s ";
|
||||
fprintf (out, flag_format, line_flag);
|
||||
}
|
||||
|
||||
output_1_line (text, limit, flag_format, line_flag);
|
||||
|
||||
if ((!line_flag || line_flag[0]) && limit[-1] != '\n')
|
||||
fprintf (out, "\n\\ No newline at end of file\n");
|
||||
}
|
||||
|
||||
/* Output a line from TEXT up to LIMIT. Without -t, output verbatim.
|
||||
With -t, expand white space characters to spaces, and if FLAG_FORMAT
|
||||
is nonzero, output it with argument LINE_FLAG after every
|
||||
internal carriage return, so that tab stops continue to line up. */
|
||||
|
||||
void
|
||||
output_1_line (text, limit, flag_format, line_flag)
|
||||
char const *text, *limit, *flag_format, *line_flag;
|
||||
{
|
||||
if (!tab_expand_flag)
|
||||
fwrite (text, sizeof (char), limit - text, outfile);
|
||||
else
|
||||
{
|
||||
register FILE *out = outfile;
|
||||
register unsigned char c;
|
||||
register char const *t = text;
|
||||
register unsigned column = 0;
|
||||
|
||||
while (t < limit)
|
||||
switch ((c = *t++))
|
||||
{
|
||||
case '\t':
|
||||
{
|
||||
unsigned spaces = TAB_WIDTH - column % TAB_WIDTH;
|
||||
column += spaces;
|
||||
do
|
||||
putc (' ', out);
|
||||
while (--spaces);
|
||||
}
|
||||
break;
|
||||
|
||||
case '\r':
|
||||
putc (c, out);
|
||||
if (flag_format && t < limit && *t != '\n')
|
||||
fprintf (out, flag_format, line_flag);
|
||||
column = 0;
|
||||
break;
|
||||
|
||||
case '\b':
|
||||
if (column == 0)
|
||||
continue;
|
||||
column--;
|
||||
putc (c, out);
|
||||
break;
|
||||
|
||||
default:
|
||||
if (ISPRINT (c))
|
||||
column++;
|
||||
putc (c, out);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
change_letter (inserts, deletes)
|
||||
int inserts, deletes;
|
||||
{
|
||||
if (!inserts)
|
||||
return 'd';
|
||||
else if (!deletes)
|
||||
return 'a';
|
||||
else
|
||||
return 'c';
|
||||
}
|
||||
|
||||
/* Translate an internal line number (an index into diff's table of lines)
|
||||
into an actual line number in the input file.
|
||||
The internal line number is LNUM. FILE points to the data on the file.
|
||||
|
||||
Internal line numbers count from 0 starting after the prefix.
|
||||
Actual line numbers count from 1 within the entire file. */
|
||||
|
||||
int
|
||||
translate_line_number (file, lnum)
|
||||
struct file_data const *file;
|
||||
int lnum;
|
||||
{
|
||||
return lnum + file->prefix_lines + 1;
|
||||
}
|
||||
|
||||
void
|
||||
translate_range (file, a, b, aptr, bptr)
|
||||
struct file_data const *file;
|
||||
int a, b;
|
||||
int *aptr, *bptr;
|
||||
{
|
||||
*aptr = translate_line_number (file, a - 1) + 1;
|
||||
*bptr = translate_line_number (file, b + 1) - 1;
|
||||
}
|
||||
|
||||
/* Print a pair of line numbers with SEPCHAR, translated for file FILE.
|
||||
If the two numbers are identical, print just one number.
|
||||
|
||||
Args A and B are internal line numbers.
|
||||
We print the translated (real) line numbers. */
|
||||
|
||||
void
|
||||
print_number_range (sepchar, file, a, b)
|
||||
int sepchar;
|
||||
struct file_data *file;
|
||||
int a, b;
|
||||
{
|
||||
int trans_a, trans_b;
|
||||
translate_range (file, a, b, &trans_a, &trans_b);
|
||||
|
||||
/* Note: we can have B < A in the case of a range of no lines.
|
||||
In this case, we should print the line number before the range,
|
||||
which is B. */
|
||||
if (trans_b > trans_a)
|
||||
fprintf (outfile, "%d%c%d", trans_a, sepchar, trans_b);
|
||||
else
|
||||
fprintf (outfile, "%d", trans_b);
|
||||
}
|
||||
|
||||
/* Look at a hunk of edit script and report the range of lines in each file
|
||||
that it applies to. HUNK is the start of the hunk, which is a chain
|
||||
of `struct change'. The first and last line numbers of file 0 are stored in
|
||||
*FIRST0 and *LAST0, and likewise for file 1 in *FIRST1 and *LAST1.
|
||||
Note that these are internal line numbers that count from 0.
|
||||
|
||||
If no lines from file 0 are deleted, then FIRST0 is LAST0+1.
|
||||
|
||||
Also set *DELETES nonzero if any lines of file 0 are deleted
|
||||
and set *INSERTS nonzero if any lines of file 1 are inserted.
|
||||
If only ignorable lines are inserted or deleted, both are
|
||||
set to 0. */
|
||||
|
||||
void
|
||||
analyze_hunk (hunk, first0, last0, first1, last1, deletes, inserts)
|
||||
struct change *hunk;
|
||||
int *first0, *last0, *first1, *last1;
|
||||
int *deletes, *inserts;
|
||||
{
|
||||
int l0, l1, show_from, show_to;
|
||||
int i;
|
||||
int trivial = ignore_blank_lines_flag || ignore_regexp_list;
|
||||
struct change *next;
|
||||
|
||||
show_from = show_to = 0;
|
||||
|
||||
*first0 = hunk->line0;
|
||||
*first1 = hunk->line1;
|
||||
|
||||
next = hunk;
|
||||
do
|
||||
{
|
||||
l0 = next->line0 + next->deleted - 1;
|
||||
l1 = next->line1 + next->inserted - 1;
|
||||
show_from += next->deleted;
|
||||
show_to += next->inserted;
|
||||
|
||||
for (i = next->line0; i <= l0 && trivial; i++)
|
||||
if (!ignore_blank_lines_flag || files[0].linbuf[i][0] != '\n')
|
||||
{
|
||||
struct regexp_list *r;
|
||||
char const *line = files[0].linbuf[i];
|
||||
int len = files[0].linbuf[i + 1] - line;
|
||||
|
||||
for (r = ignore_regexp_list; r; r = r->next)
|
||||
if (0 <= re_search (&r->buf, line, len, 0, len, 0))
|
||||
break; /* Found a match. Ignore this line. */
|
||||
/* If we got all the way through the regexp list without
|
||||
finding a match, then it's nontrivial. */
|
||||
if (!r)
|
||||
trivial = 0;
|
||||
}
|
||||
|
||||
for (i = next->line1; i <= l1 && trivial; i++)
|
||||
if (!ignore_blank_lines_flag || files[1].linbuf[i][0] != '\n')
|
||||
{
|
||||
struct regexp_list *r;
|
||||
char const *line = files[1].linbuf[i];
|
||||
int len = files[1].linbuf[i + 1] - line;
|
||||
|
||||
for (r = ignore_regexp_list; r; r = r->next)
|
||||
if (0 <= re_search (&r->buf, line, len, 0, len, 0))
|
||||
break; /* Found a match. Ignore this line. */
|
||||
/* If we got all the way through the regexp list without
|
||||
finding a match, then it's nontrivial. */
|
||||
if (!r)
|
||||
trivial = 0;
|
||||
}
|
||||
}
|
||||
while ((next = next->link) != 0);
|
||||
|
||||
*last0 = l0;
|
||||
*last1 = l1;
|
||||
|
||||
/* If all inserted or deleted lines are ignorable,
|
||||
tell the caller to ignore this hunk. */
|
||||
|
||||
if (trivial)
|
||||
show_from = show_to = 0;
|
||||
|
||||
*deletes = show_from;
|
||||
*inserts = show_to;
|
||||
}
|
||||
|
||||
/* Concatenate three strings, returning a newly malloc'd string. */
|
||||
|
||||
char *
|
||||
concat (s1, s2, s3)
|
||||
char const *s1, *s2, *s3;
|
||||
{
|
||||
size_t len = strlen (s1) + strlen (s2) + strlen (s3);
|
||||
char *new = xmalloc (len + 1);
|
||||
sprintf (new, "%s%s%s", s1, s2, s3);
|
||||
return new;
|
||||
}
|
||||
|
||||
/* Yield the newly malloc'd pathname
|
||||
of the file in DIR whose filename is FILE. */
|
||||
|
||||
char *
|
||||
dir_file_pathname (dir, file)
|
||||
char const *dir, *file;
|
||||
{
|
||||
char const *p = filename_lastdirchar (dir);
|
||||
return concat (dir, "/" + (p && !p[1]), file);
|
||||
}
|
||||
|
||||
void
|
||||
debug_script (sp)
|
||||
struct change *sp;
|
||||
{
|
||||
fflush (stdout);
|
||||
for (; sp; sp = sp->link)
|
||||
fprintf (stderr, "%3d %3d delete %d insert %d\n",
|
||||
sp->line0, sp->line1, sp->deleted, sp->inserted);
|
||||
fflush (stderr);
|
||||
}
|
||||
@@ -1,5 +0,0 @@
|
||||
/* Version number of GNU diff. */
|
||||
|
||||
#include <config.h>
|
||||
|
||||
char const diff_version_string[] = "2.7";
|
||||
@@ -1,115 +0,0 @@
|
||||
/* fncase.c -- CVS support for case insensitive file systems.
|
||||
Jim Blandy <[email protected]>
|
||||
|
||||
This file is part of GNU CVS.
|
||||
|
||||
GNU CVS is free software; you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by the
|
||||
Free Software Foundation; either version 2, or (at your option) any
|
||||
later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details. */
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include "system.h"
|
||||
|
||||
/* The equivalence class mapping for filenames.
|
||||
Windows NT filenames are case-insensitive, but case-preserving.
|
||||
Both / and \ are path element separators.
|
||||
Thus, this table maps both upper and lower case to lower case, and
|
||||
both / and \ to /. */
|
||||
|
||||
#if 0
|
||||
main ()
|
||||
{
|
||||
int c;
|
||||
|
||||
for (c = 0; c < 256; c++)
|
||||
{
|
||||
int t;
|
||||
|
||||
if (c == '\\')
|
||||
t = '/';
|
||||
else
|
||||
t = tolower (c);
|
||||
|
||||
if ((c & 0x7) == 0x0)
|
||||
printf (" ");
|
||||
printf ("0x%02x,", t);
|
||||
if ((c & 0x7) == 0x7)
|
||||
putchar ('\n');
|
||||
else if ((c & 0x7) == 0x3)
|
||||
putchar (' ');
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
unsigned char
|
||||
WNT_filename_classes[] =
|
||||
{
|
||||
0x00,0x01,0x02,0x03, 0x04,0x05,0x06,0x07,
|
||||
0x08,0x09,0x0a,0x0b, 0x0c,0x0d,0x0e,0x0f,
|
||||
0x10,0x11,0x12,0x13, 0x14,0x15,0x16,0x17,
|
||||
0x18,0x19,0x1a,0x1b, 0x1c,0x1d,0x1e,0x1f,
|
||||
0x20,0x21,0x22,0x23, 0x24,0x25,0x26,0x27,
|
||||
0x28,0x29,0x2a,0x2b, 0x2c,0x2d,0x2e,0x2f,
|
||||
0x30,0x31,0x32,0x33, 0x34,0x35,0x36,0x37,
|
||||
0x38,0x39,0x3a,0x3b, 0x3c,0x3d,0x3e,0x3f,
|
||||
0x40,0x61,0x62,0x63, 0x64,0x65,0x66,0x67,
|
||||
0x68,0x69,0x6a,0x6b, 0x6c,0x6d,0x6e,0x6f,
|
||||
0x70,0x71,0x72,0x73, 0x74,0x75,0x76,0x77,
|
||||
0x78,0x79,0x7a,0x5b, 0x2f,0x5d,0x5e,0x5f,
|
||||
0x60,0x61,0x62,0x63, 0x64,0x65,0x66,0x67,
|
||||
0x68,0x69,0x6a,0x6b, 0x6c,0x6d,0x6e,0x6f,
|
||||
0x70,0x71,0x72,0x73, 0x74,0x75,0x76,0x77,
|
||||
0x78,0x79,0x7a,0x7b, 0x7c,0x7d,0x7e,0x7f,
|
||||
0x80,0x81,0x82,0x83, 0x84,0x85,0x86,0x87,
|
||||
0x88,0x89,0x8a,0x8b, 0x8c,0x8d,0x8e,0x8f,
|
||||
0x90,0x91,0x92,0x93, 0x94,0x95,0x96,0x97,
|
||||
0x98,0x99,0x9a,0x9b, 0x9c,0x9d,0x9e,0x9f,
|
||||
0xa0,0xa1,0xa2,0xa3, 0xa4,0xa5,0xa6,0xa7,
|
||||
0xa8,0xa9,0xaa,0xab, 0xac,0xad,0xae,0xaf,
|
||||
0xb0,0xb1,0xb2,0xb3, 0xb4,0xb5,0xb6,0xb7,
|
||||
0xb8,0xb9,0xba,0xbb, 0xbc,0xbd,0xbe,0xbf,
|
||||
0xc0,0xc1,0xc2,0xc3, 0xc4,0xc5,0xc6,0xc7,
|
||||
0xc8,0xc9,0xca,0xcb, 0xcc,0xcd,0xce,0xcf,
|
||||
0xd0,0xd1,0xd2,0xd3, 0xd4,0xd5,0xd6,0xd7,
|
||||
0xd8,0xd9,0xda,0xdb, 0xdc,0xdd,0xde,0xdf,
|
||||
0xe0,0xe1,0xe2,0xe3, 0xe4,0xe5,0xe6,0xe7,
|
||||
0xe8,0xe9,0xea,0xeb, 0xec,0xed,0xee,0xef,
|
||||
0xf0,0xf1,0xf2,0xf3, 0xf4,0xf5,0xf6,0xf7,
|
||||
0xf8,0xf9,0xfa,0xfb, 0xfc,0xfd,0xfe,0xff,
|
||||
};
|
||||
|
||||
/* Like strcmp, but with the appropriate tweaks for file names.
|
||||
Under Windows NT, filenames are case-insensitive but case-preserving,
|
||||
and both \ and / are path element separators. */
|
||||
int
|
||||
fncmp (const char *n1, const char *n2)
|
||||
{
|
||||
while (*n1 && *n2
|
||||
&& (WNT_filename_classes[(unsigned char) *n1]
|
||||
== WNT_filename_classes[(unsigned char) *n2]))
|
||||
n1++, n2++;
|
||||
return (WNT_filename_classes[(unsigned char) *n1]
|
||||
- WNT_filename_classes[(unsigned char) *n2]);
|
||||
}
|
||||
|
||||
/* Fold characters in FILENAME to their canonical forms.
|
||||
If FOLD_FN_CHAR is not #defined, the system provides a default
|
||||
definition for this. */
|
||||
void
|
||||
fnfold (char *filename)
|
||||
{
|
||||
while (*filename)
|
||||
{
|
||||
*filename = FOLD_FN_CHAR (*filename);
|
||||
filename++;
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large.
Load diff
@@ -1,298 +0,0 @@
|
||||
/* This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details. */
|
||||
|
||||
/* Collect and manage hardlink info associated with a particular file. */
|
||||
|
||||
#include "cvs.h"
|
||||
#include "hardlink.h"
|
||||
|
||||
/* The structure currently used to manage hardlink info is a list.
|
||||
Therefore, most of the functions which manipulate hardlink data
|
||||
are walklist procedures. This is not a very efficient implementation;
|
||||
if someone decides to use a real hash table (for instance), then
|
||||
much of this code can be rewritten to be a little less arcane.
|
||||
|
||||
Each element of `hardlist' represents an inode. It is keyed on the
|
||||
inode number, and points to a list of files. This is to make it
|
||||
easy to find out what files are linked to a given file FOO: find
|
||||
FOO's inode, look it up in hardlist, and retrieve the list of files
|
||||
associated with that inode.
|
||||
|
||||
Each file node, in turn, is represented by a `hardlink_info' struct,
|
||||
which includes `status' and `links' fields. The `status' field should
|
||||
be used by a procedure like commit_fileproc or update_fileproc to
|
||||
record each file's status; that way, after all file links have been
|
||||
recorded, CVS can check the linkage of files which are in doubt
|
||||
(i.e. T_NEEDS_MERGE files).
|
||||
|
||||
TODO: a diagram of an example hardlist would help here. */
|
||||
|
||||
/* TODO: change this to something with a marginal degree of
|
||||
efficiency, like maybe a hash table. Yeah. */
|
||||
|
||||
List *hardlist; /* Record hardlink information for working files */
|
||||
char *working_dir; /* The top-level working directory, used for
|
||||
constructing full pathnames. */
|
||||
|
||||
/* For check_link_proc: list all of the files named in an inode list. */
|
||||
static int
|
||||
list_files_proc (node, vstrp)
|
||||
Node *node;
|
||||
void *vstrp;
|
||||
{
|
||||
char **strp, *file;
|
||||
int len;
|
||||
|
||||
/* Get the file's basename. This is because -- VERY IMPORTANT --
|
||||
the `hardlinks' field is presently defined only to include links
|
||||
within a directory. So the hardlinks field might be `foo' or
|
||||
`mumble grump flink', but not `foo bar com/baz' or `wham ../bam
|
||||
../thank/you'. Someday it would be nice to extend this to
|
||||
permit cross-directory links, but the issues involved are
|
||||
hideous. */
|
||||
|
||||
file = strrchr (node->key, '/');
|
||||
if (file)
|
||||
++file;
|
||||
else
|
||||
file = node->key;
|
||||
|
||||
/* Is it safe to cast vstrp to (char **) here, and then play with
|
||||
the contents? I think so, since vstrp will have started out
|
||||
a char ** to begin with, so we should not have alignment bugs. */
|
||||
strp = (char **) vstrp;
|
||||
len = (*strp == NULL ? 0 : strlen (*strp));
|
||||
*strp = (char *) xrealloc (*strp, len + strlen (file) + 2);
|
||||
if (*strp == NULL)
|
||||
{
|
||||
error (0, errno, "could not allocate memory");
|
||||
return 1;
|
||||
}
|
||||
if (sprintf (*strp + len, "%s ", file) < 0)
|
||||
{
|
||||
error (0, errno, "could not compile file list");
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Set the link field of each hardlink_info node to `data', which is a
|
||||
list of linked files. */
|
||||
static int
|
||||
set_hardlink_field_proc (node, data)
|
||||
Node *node;
|
||||
void *data;
|
||||
{
|
||||
struct hardlink_info *hlinfo = (struct hardlink_info *) node->data;
|
||||
hlinfo->links = xstrdup ((char *) data);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* For each file being checked in, compile a list of the files linked
|
||||
to it, and cache the list in the file's hardlink_info field. */
|
||||
int
|
||||
cache_hardlinks_proc (node, data)
|
||||
Node *node;
|
||||
void *data;
|
||||
{
|
||||
List *inode_links;
|
||||
char *p, *linked_files = NULL;
|
||||
int err;
|
||||
|
||||
inode_links = (List *) node->data;
|
||||
|
||||
/* inode->data is a list of hardlink_info structures: all the
|
||||
files linked to this inode. We compile a string of each file
|
||||
named in this list, in alphabetical order, separated by spaces.
|
||||
Then store this string in the `links' field of each
|
||||
hardlink_info structure, so that RCS_checkin can easily add
|
||||
it to the `hardlinks' field of a new delta node. */
|
||||
|
||||
sortlist (inode_links, fsortcmp);
|
||||
err = walklist (inode_links, list_files_proc, &linked_files);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
/* Trim trailing whitespace. */
|
||||
p = linked_files + strlen(linked_files) - 1;
|
||||
while (p > linked_files && isspace (*p))
|
||||
*p-- = '\0';
|
||||
|
||||
err = walklist (inode_links, set_hardlink_field_proc, linked_files);
|
||||
return err;
|
||||
}
|
||||
|
||||
/* Return a pointer to FILEPATH's node in the hardlist. This means
|
||||
looking up its inode, retrieving the list of files linked to that
|
||||
inode, and then looking up FILE in that list. If the file doesn't
|
||||
seem to exist, return NULL. */
|
||||
Node *
|
||||
lookup_file_by_inode (filepath)
|
||||
const char *filepath;
|
||||
{
|
||||
char *inodestr, *file;
|
||||
struct stat sb;
|
||||
Node *hp, *p;
|
||||
|
||||
/* Get file's basename, so that we can stat it. */
|
||||
file = strrchr (filepath, '/');
|
||||
if (file)
|
||||
++file;
|
||||
else
|
||||
file = (char *) filepath;
|
||||
|
||||
/* inodestr contains the hexadecimal representation of an
|
||||
inode, so it requires two bytes of text to represent
|
||||
each byte of the inode number. */
|
||||
inodestr = (char *) xmalloc (2*sizeof(ino_t)*sizeof(char) + 1);
|
||||
if (stat (file, &sb) < 0)
|
||||
{
|
||||
if (errno == ENOENT)
|
||||
{
|
||||
/* The file doesn't exist; we may be doing an update on a
|
||||
file that's been removed. A nonexistent file has no
|
||||
link information, so return without changing hardlist. */
|
||||
free (inodestr);
|
||||
return NULL;
|
||||
}
|
||||
error (1, errno, "cannot stat %s", file);
|
||||
}
|
||||
|
||||
sprintf (inodestr, "%lx", (unsigned long) sb.st_ino);
|
||||
|
||||
/* Find out if this inode is already in the hardlist, adding
|
||||
a new entry to the list if not. */
|
||||
hp = findnode (hardlist, inodestr);
|
||||
if (hp == NULL)
|
||||
{
|
||||
hp = getnode ();
|
||||
hp->type = UNKNOWN;
|
||||
hp->key = inodestr;
|
||||
hp->data = (char *) getlist();
|
||||
hp->delproc = dellist;
|
||||
(void) addnode (hardlist, hp);
|
||||
}
|
||||
else
|
||||
{
|
||||
free (inodestr);
|
||||
}
|
||||
|
||||
p = findnode ((List *) hp->data, filepath);
|
||||
if (p == NULL)
|
||||
{
|
||||
p = getnode();
|
||||
p->type = UNKNOWN;
|
||||
p->key = xstrdup (filepath);
|
||||
p->data = NULL;
|
||||
(void) addnode ((List *) hp->data, p);
|
||||
}
|
||||
|
||||
return p;
|
||||
}
|
||||
|
||||
/* After a file has been checked out, add a node for it to the hardlist
|
||||
(if necessary) and mark it as checked out. */
|
||||
void
|
||||
update_hardlink_info (file)
|
||||
const char *file;
|
||||
{
|
||||
char *path;
|
||||
Node *n;
|
||||
struct hardlink_info *hlinfo;
|
||||
|
||||
if (file[0] == '/')
|
||||
{
|
||||
path = xstrdup (file);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* file is a relative pathname; assume it's from the current
|
||||
working directory. */
|
||||
char *dir = xgetwd();
|
||||
path = xmalloc (sizeof(char) * (strlen(dir) + strlen(file) + 2));
|
||||
sprintf (path, "%s/%s", dir, file);
|
||||
free (dir);
|
||||
}
|
||||
|
||||
n = lookup_file_by_inode (path);
|
||||
if (n == NULL)
|
||||
{
|
||||
/* Something is *really* wrong if the file doesn't exist here;
|
||||
update_hardlink_info should be called only when a file has
|
||||
just been checked out to a working directory. */
|
||||
error (1, 0, "lost hardlink info for %s", file);
|
||||
}
|
||||
|
||||
if (n->data == NULL)
|
||||
n->data = (char *) xmalloc (sizeof (struct hardlink_info));
|
||||
hlinfo = (struct hardlink_info *) n->data;
|
||||
hlinfo->status = T_UPTODATE;
|
||||
hlinfo->checked_out = 1;
|
||||
hlinfo->links = NULL;
|
||||
}
|
||||
|
||||
/* Return a string listing all the files known to be linked to FILE in
|
||||
the working directory. Used by special_file_mismatch, to determine
|
||||
whether it is safe to merge two files. */
|
||||
char *
|
||||
list_files_linked_to (file)
|
||||
const char *file;
|
||||
{
|
||||
char *inodestr, *filelist, *path;
|
||||
struct stat sb;
|
||||
Node *n;
|
||||
int err;
|
||||
|
||||
/* If hardlist is NULL, we have not been doing an operation that
|
||||
would permit us to know anything about the file's hardlinks
|
||||
(cvs update, cvs commit, etc). Return an empty string. */
|
||||
if (hardlist == NULL)
|
||||
return xstrdup ("");
|
||||
|
||||
/* Get the full pathname of file (assuming the working directory) */
|
||||
if (file[0] == '/')
|
||||
path = xstrdup (file);
|
||||
else
|
||||
{
|
||||
char *dir = xgetwd();
|
||||
path = (char *) xmalloc (sizeof(char) *
|
||||
(strlen(dir) + strlen(file) + 2));
|
||||
sprintf (path, "%s/%s", dir, file);
|
||||
free (dir);
|
||||
}
|
||||
|
||||
/* We do an extra lookup_file here just to make sure that there
|
||||
is a node for `path' in the hardlist. If that were not so,
|
||||
comparing the working directory linkage against the repository
|
||||
linkage for a file would always fail. */
|
||||
(void) lookup_file_by_inode (path);
|
||||
|
||||
if (stat (path, &sb) < 0)
|
||||
error (1, errno, "cannot stat %s", file);
|
||||
/* inodestr contains the hexadecimal representation of an
|
||||
inode, so it requires two bytes of text to represent
|
||||
each byte of the inode number. */
|
||||
inodestr = (char *) xmalloc (2*sizeof(ino_t)*sizeof(char) + 1);
|
||||
sprintf (inodestr, "%lx", (unsigned long) sb.st_ino);
|
||||
|
||||
/* Make sure the files linked to this inode are sorted. */
|
||||
n = findnode (hardlist, inodestr);
|
||||
sortlist ((List *) n->data, fsortcmp);
|
||||
|
||||
filelist = NULL;
|
||||
err = walklist ((List *) n->data, list_files_proc, &filelist);
|
||||
if (err)
|
||||
error (1, 0, "cannot get list of hardlinks for %s", file);
|
||||
|
||||
free (inodestr);
|
||||
return filelist;
|
||||
}
|
||||
@@ -1,33 +0,0 @@
|
||||
/* This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details. */
|
||||
|
||||
/* Data type definitions and declarations for hardlink management. */
|
||||
|
||||
/* This file should be #included in CVS source files after cvs.h
|
||||
since it relies on types and macros defined there. */
|
||||
|
||||
/* The `checked_out' member of a hardlink_info struct is used only
|
||||
when files are being checked out or updated. It is used only when
|
||||
hardlinked files are being checked out. */
|
||||
|
||||
struct hardlink_info
|
||||
{
|
||||
Ctype status; /* as returned from Classify_File() */
|
||||
int checked_out; /* has this file been checked out lately? */
|
||||
char *links; /* contents of `hardlinks' RCS field */
|
||||
};
|
||||
|
||||
extern List *hardlist;
|
||||
extern char *working_dir;
|
||||
|
||||
int cache_hardlinks_proc PROTO ((Node *, void *));
|
||||
Node *lookup_file_by_inode PROTO ((const char *));
|
||||
void update_hardlink_info PROTO ((const char *));
|
||||
char *list_files_linked_to PROTO ((const char *));
|
||||
@@ -1,20 +0,0 @@
|
||||
# $Id: Makefile,v 1.14 1997/05/15 23:00:07 peter Exp $
|
||||
|
||||
.include "${.CURDIR}/../Makefile.inc"
|
||||
|
||||
.PATH: ${CVSDIR}/diff
|
||||
|
||||
LIB= diff
|
||||
|
||||
NOPROFILE= yes
|
||||
NOPIC= yes
|
||||
|
||||
CFLAGS+= -I${.CURDIR} -I${.CURDIR}/../lib -I${CVSDIR}/lib -DHAVE_CONFIG_H
|
||||
|
||||
SRCS = diff.c diff3.c analyze.c cmpbuf.c cmpbuf.h io.c context.c ed.c \
|
||||
normal.c ifdef.c util.c dir.c version.c diff.h side.c
|
||||
|
||||
install:
|
||||
@echo -n
|
||||
|
||||
.include <bsd.lib.mk>
|
||||
@@ -1,47 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 John Birrell <[email protected]>.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by John Birrell.
|
||||
* 4. Neither the name of the author nor the names of any co-contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY JOHN BIRRELL AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
|
||||
extern int errno;
|
||||
|
||||
/*
|
||||
* Declare a weak reference in case the application is not linked
|
||||
* with libpthread.
|
||||
*/
|
||||
#pragma weak __error=__error_unthreaded
|
||||
|
||||
int * __error_unthreaded()
|
||||
{
|
||||
return(&errno);
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
# $Id: Makefile,v 1.1 1997/07/16 12:24:18 julian Exp $
|
||||
#
|
||||
SUBDIR= write_mfs_in_kernel dumpnlist
|
||||
|
||||
.include <bsd.subdir.mk>
|
||||
|
||||
|
||||
@@ -1,71 +0,0 @@
|
||||
:
|
||||
#set -ex
|
||||
|
||||
VNDEVICE=vn0
|
||||
export BLOCKSIZE=512
|
||||
|
||||
BOOTBLKDIR=$1 ; shift
|
||||
MNT=$1 ; shift
|
||||
FSSIZE=$1 ; shift
|
||||
FSPROTO=$1 ; shift
|
||||
FSINODE=$1 ; shift
|
||||
FSLABEL=$1 ; shift
|
||||
|
||||
deadlock=20
|
||||
|
||||
while true
|
||||
do
|
||||
rm -f fs-image
|
||||
|
||||
if [ ! -b /dev/${VNDEVICE} -o ! -c /dev/r${VNDEVICE} ] ; then
|
||||
( cd /dev && sh MAKEDEV ${VNDEVICE} )
|
||||
fi
|
||||
|
||||
umount /dev/${VNDEVICE} 2>/dev/null || true
|
||||
|
||||
umount ${MNT} 2>/dev/null || true
|
||||
|
||||
vnconfig -u /dev/r${VNDEVICE} 2>/dev/null || true
|
||||
|
||||
dd of=fs-image if=/dev/zero count=${FSSIZE} bs=1k 2>/dev/null
|
||||
# this suppresses the `invalid primary partition table: no magic'
|
||||
awk 'BEGIN {printf "%c%c", 85, 170}' |\
|
||||
dd of=fs-image obs=1 seek=510 conv=notrunc 2>/dev/null
|
||||
|
||||
vnconfig -s labels -c /dev/r${VNDEVICE} fs-image
|
||||
|
||||
disklabel -Brw \
|
||||
-b ${BOOTBLKDIR}/boot1 \
|
||||
-s ${BOOTBLKDIR}/boot2 \
|
||||
/dev/r${VNDEVICE} minimum
|
||||
|
||||
TPC=1
|
||||
CPD=1
|
||||
SPT=$(( 2 * $FSSIZE / 2))
|
||||
newfs -u ${SPT} -t ${TPC} -s $(( ${FSSIZE} * 2 )) -i ${FSINODE} -m 0 -o space /dev/r${VNDEVICE}c
|
||||
|
||||
mount /dev/${VNDEVICE}c ${MNT}
|
||||
|
||||
( set -e && cd ${FSPROTO} && find . -print | cpio -dump ${MNT} )
|
||||
|
||||
df -ki /mnt
|
||||
|
||||
set `df -ki /mnt | tail -1`
|
||||
|
||||
umount ${MNT}
|
||||
|
||||
fsck -p /dev/r${VNDEVICE}c < /dev/null
|
||||
|
||||
vnconfig -u /dev/r${VNDEVICE} 2>/dev/null || true
|
||||
|
||||
if [ $FSLABEL != "minimum" ] ; then
|
||||
echo ${FSSIZE} > fs-image.size
|
||||
break
|
||||
fi
|
||||
|
||||
echo ">>> Filesystem is ${FSSIZE} K, $4 left"
|
||||
echo ">>> ${FSINODE} bytes/inode, $7 left"
|
||||
echo ">>> `expr ${FSSIZE} \* 1024 / ${FSINODE}`"
|
||||
echo ${FSSIZE} > fs-image.size
|
||||
break;
|
||||
done
|
||||
@@ -1,8 +0,0 @@
|
||||
# $Id: Makefile,v 1.1 1997/07/16 12:24:19 julian Exp $
|
||||
#
|
||||
PROG=dumpnlist
|
||||
NOMAN=yes
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
|
||||
|
||||
@@ -1,44 +0,0 @@
|
||||
#include <sys/types.h>
|
||||
#include <sys/fcntl.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <nlist.h>
|
||||
#include <stdio.h>
|
||||
|
||||
struct nlist nl[] = {
|
||||
{"_isa_devtab_bio"},
|
||||
{"_isa_devtab_tty"},
|
||||
{"_isa_devtab_net"},
|
||||
{"_isa_devtab_null"},
|
||||
{"_isa_biotab_wdc"},
|
||||
{"_isa_biotab_fdc"},
|
||||
{"_eisadriver_set"},
|
||||
{"_eisa_dev_list"},
|
||||
{"_pcidevice_set"},
|
||||
{"_device_list"},
|
||||
{"_scbusses"},
|
||||
{"_scsi_cinit"},
|
||||
{"_scsi_dinit"},
|
||||
{"_scsi_tinit"},
|
||||
{""},
|
||||
};
|
||||
|
||||
int
|
||||
main(int ac, char **av)
|
||||
{
|
||||
int i;
|
||||
|
||||
i = nlist(av[1], nl);
|
||||
if (i == -1) {
|
||||
fprintf(stderr, "nlist returns error for %s\n", av[1]);
|
||||
perror("nlist");
|
||||
return 1;
|
||||
}
|
||||
printf("%d\n", sizeof(nl) / sizeof(struct nlist));
|
||||
for (i = 0; nl[i].n_name; i++) {
|
||||
printf("%s\n", nl[i].n_name);
|
||||
printf("%d %d %d %ld\n",
|
||||
nl[i].n_type, nl[i].n_other, nl[i].n_desc, nl[i].n_value);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@@ -1,8 +0,0 @@
|
||||
# $Id: Makefile,v 1.1 1997/07/16 12:24:20 julian Exp $
|
||||
#
|
||||
PROG=write_mfs_in_kernel
|
||||
NOMAN=yes
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
|
||||
|
||||
@@ -1,70 +0,0 @@
|
||||
/*
|
||||
* ----------------------------------------------------------------------------
|
||||
* "THE BEER-WARE LICENSE" (Revision 42):
|
||||
* <[email protected]> wrote this file. As long as you retain this notice you
|
||||
* can do whatever you want with this stuff. If we meet some day, and you think
|
||||
* this stuff is worth it, you can buy me a beer in return. Poul-Henning Kamp
|
||||
* ----------------------------------------------------------------------------
|
||||
*
|
||||
* $Id: write_mfs_in_kernel.c,v 1.1 1997/07/16 12:24:21 julian Exp $
|
||||
*
|
||||
* This program patches a filesystem into a kernel made with MFS_ROOT
|
||||
* option.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/stat.h>
|
||||
#include <ufs/ffs/fs.h>
|
||||
|
||||
main(int argc, char **argv)
|
||||
{
|
||||
unsigned char *buf_kernel, *buf_fs, *p,*q;
|
||||
int fd_kernel, fd_fs;
|
||||
struct stat st_kernel, st_fs;
|
||||
u_long l;
|
||||
|
||||
if (argc < 3) {
|
||||
fprintf(stderr,"Usage:\n\t%s kernel fs\n");
|
||||
exit(2);
|
||||
}
|
||||
fd_kernel = open(argv[1],O_RDWR);
|
||||
if (fd_kernel < 0) { perror(argv[1]); exit(2); }
|
||||
fstat(fd_kernel,&st_kernel);
|
||||
fd_fs = open(argv[2],O_RDONLY);
|
||||
if (fd_fs < 0) { perror(argv[2]); exit(2); }
|
||||
fstat(fd_fs,&st_fs);
|
||||
buf_kernel = malloc(st_kernel.st_size);
|
||||
if (!buf_kernel) { perror("malloc"); exit(2); }
|
||||
buf_fs = malloc(st_fs.st_size);
|
||||
if (!buf_fs) { perror("malloc"); exit(2); }
|
||||
if (st_kernel.st_size != read(fd_kernel,buf_kernel,st_kernel.st_size))
|
||||
{ perror(argv[1]); exit(2); }
|
||||
if (st_fs.st_size != read(fd_fs,buf_fs,st_fs.st_size))
|
||||
{ perror(argv[2]); exit(2); }
|
||||
for(l=0,p=buf_kernel; l < st_kernel.st_size - st_fs.st_size ; l++,p++ )
|
||||
if(*p == 'M' && !strcmp(p,"MFS Filesystem goes here"))
|
||||
goto found;
|
||||
fprintf(stderr,"MFS filesystem signature not found in %s\n",argv[1]);
|
||||
exit(1);
|
||||
found:
|
||||
for(l=0,q= p + SBOFF; l < st_fs.st_size - SBOFF ; l++,q++ )
|
||||
if (*q)
|
||||
goto fail;
|
||||
memcpy(p+SBOFF,buf_fs+SBOFF,st_fs.st_size-SBOFF);
|
||||
lseek(fd_kernel,0L,SEEK_SET);
|
||||
if (st_kernel.st_size != write(fd_kernel,buf_kernel,st_kernel.st_size))
|
||||
{ perror(argv[1]); exit(2); }
|
||||
exit(0);
|
||||
fail:
|
||||
l += SBOFF;
|
||||
fprintf(stderr,"Obstruction in kernel after %ld bytes (%ld Kbyte)\n",
|
||||
l, l/1024);
|
||||
fprintf(stderr,"Filesystem is %ld bytes (%ld Kbyte)\n",
|
||||
(u_long)st_fs.st_size, (u_long)st_fs.st_size/1024);
|
||||
exit(1);
|
||||
}
|
||||
@@ -1,108 +0,0 @@
|
||||
###
|
||||
# $Id: crunch_fs.mk,v 1.1 1997/07/16 12:24:29 julian Exp $
|
||||
#
|
||||
# This is included to make a floppy that includes a crunch file
|
||||
#
|
||||
# Variables that control this mk include file.
|
||||
# TOP specifies where the top of the FreeBSD source tree is.. (*)
|
||||
# FS_DIRS directories to make on the fs (*)
|
||||
# STANDLINKS added symlinks to /stand on the fs
|
||||
# VERBATIM a directory that contains tree to be copied to the fs
|
||||
# FSSIZE defaults to 1440
|
||||
# FSLABEL defaults to fd1440
|
||||
# FSINODE defaults to 4000
|
||||
# FS_DEVICES devices to make on the fs (using MAKEDEV) (default = all)
|
||||
# ZIP decides if the installed cruch will also be gzip'd(def=true)
|
||||
# (*) = Mandatory
|
||||
###
|
||||
|
||||
# If we weren't told, default to nothing
|
||||
.if ! defined( TOP )
|
||||
# define TOP!
|
||||
xxx
|
||||
.endif
|
||||
|
||||
# mountpoint for filesystems.
|
||||
MNT= /mnt
|
||||
|
||||
# other floppy parameters.
|
||||
FSSIZE?= 1440
|
||||
FSLABEL?= fd1440
|
||||
FSINODE?= 2000
|
||||
FS_DEVICES?= all
|
||||
ZIP?=true
|
||||
|
||||
# Things which will get you into trouble if you change them
|
||||
TREE= tree
|
||||
LABELDIR= ${OBJTOP}/sys/i386/boot/biosboot
|
||||
|
||||
clean:
|
||||
rm -rf tree fs-image fs-image.size step[0-9]
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
|
||||
|
||||
#
|
||||
# --==## Create a filesystem image ##==--
|
||||
#
|
||||
|
||||
fs_image: ${TREE} step2 step3 step4 fs-image
|
||||
|
||||
${TREE}: ${.CURDIR}/Makefile
|
||||
rm -rf ${TREE}
|
||||
mkdir -p ${TREE}
|
||||
cd ${TREE} && mkdir ${FS_DIRS}
|
||||
cd ${TREE} ; for i in ${STANDLINKS} ; \
|
||||
do \
|
||||
ln -s /stand $${i} ; \
|
||||
done
|
||||
|
||||
step2: ${.CURDIR}/${CRUNCHDIRS} ${.CURDIR}/Makefile
|
||||
.if defined(CRUNCHDIRS)
|
||||
@cd ${.CURDIR} && $(MAKE) installCRUNCH DIR=${TREE}/stand ZIP=${ZIP}
|
||||
.endif
|
||||
touch step2
|
||||
|
||||
step3: step2
|
||||
.if defined (FS_DEVICES)
|
||||
( cd tree/dev && \
|
||||
cp ${TOP}/etc/etc.i386/MAKEDEV . && sh MAKEDEV ${FS_DEVICES} )
|
||||
.endif
|
||||
touch step3
|
||||
|
||||
step4: step3
|
||||
.if defined(VERBATIM)
|
||||
A=`pwd`;cd ${.CURDIR}/${VERBATIM}; \
|
||||
find . \! \( -name CVS -and -prune \) -print |cpio -pdmuv $$A/tree
|
||||
.endif
|
||||
true || cp ${TOP}/etc/spwd.db tree/etc
|
||||
touch step4
|
||||
|
||||
fs-image: step4
|
||||
sh -e ${SCRIPTDIR}/doFS.sh ${LABELDIR} ${MNT} ${FSSIZE} tree \
|
||||
${FSINODE} ${FSLABEL}
|
||||
cp fs-image.size ${.CURDIR}
|
||||
|
||||
|
||||
.if defined(CRUNCHDIRS)
|
||||
installCRUNCH:
|
||||
.if !defined(DIR)
|
||||
@echo "DIR undefined in installCRUNCH" && exit 1
|
||||
.endif
|
||||
.if !defined(ZIP)
|
||||
@echo "ZIP undefined in installCRUNCH" && exit 1
|
||||
.endif
|
||||
.for CRUNCHDIR in ${CRUNCHDIRS}
|
||||
if ${ZIP} ; then \
|
||||
gzip -9 < ${CRUNCHDIR}/crunch > ${DIR}/.crunch ; \
|
||||
else \
|
||||
ln -f ${CRUNCHDIR}/crunch ${DIR}/.crunch ; \
|
||||
fi
|
||||
chmod 555 ${DIR}/.crunch
|
||||
for i in `crunchgen -l ${.CURDIR}/${CRUNCHDIR}/crunch.conf` ; do \
|
||||
ln -f ${DIR}/.crunch ${DIR}/$$i ; \
|
||||
done
|
||||
rm -f ${DIR}/.crunch
|
||||
.endfor
|
||||
.endif
|
||||
|
||||
@@ -1,25 +0,0 @@
|
||||
|
||||
|
||||
SYSINSTALL= ${OBJTOP}/release/sysinstall/sysinstall
|
||||
|
||||
NOCRYPT?= yes
|
||||
|
||||
all: crunch
|
||||
|
||||
crunch:
|
||||
-crunchgen ${.CURDIR}/crunch.conf
|
||||
${MAKE} -f crunch.mk all NOCRYP=${NOCRYPT} \
|
||||
"CFLAGS=${CFLAGS} -DCRUNCHED_BINARY"
|
||||
|
||||
clean:
|
||||
rm -f *.o *.stub *.lo *_stub.c *.mk \
|
||||
crunch.cache \
|
||||
crunch.mk \
|
||||
crunch.c \
|
||||
crunch \
|
||||
.tmp_*
|
||||
|
||||
install:
|
||||
@echo " No idea what to do to install yet"
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,50 +0,0 @@
|
||||
0x2500 0x2502 0x250c 0x2510 0x2514 0x2518 0x251c 0x2524
|
||||
0x252c 0x2534 0x253c 0x2580 0x2584 0x2588 0x258c 0x2590
|
||||
0x2591 0x2592 0x2593 0x2320 0x25a0 0x2219 0x221a 0x2248
|
||||
0x2264 0x2265 0x00a0 0x2321 0x00b0 0x00b2 0x00b7 0x00f7
|
||||
0x2550 0x2551 0x2552 0x0451 0x2553 0x2554 0x2555 0x2556
|
||||
0x2557 0x2558 0x2559 0x255a 0x255b 0x255c 0x255d 0x255e
|
||||
0x255f 0x2560 0x2561 0x0401 0x2562 0x2563 0x2564 0x2565
|
||||
0x2566 0x2567 0x2568 0x2569 0x256a 0x256b 0x256c 0x00a9
|
||||
0x044e 0x0430 0x0431 0x0446 0x0434 0x0435 0x0444 0x0433
|
||||
0x0445 0x0438 0x0439 0x043a 0x043b 0x043c 0x043d 0x043e
|
||||
0x043f 0x044f 0x0440 0x0441 0x0442 0x0443 0x0436 0x0432
|
||||
0x044c 0x044b 0x0437 0x0448 0x044d 0x0449 0x0447 0x044a
|
||||
0x042e 0x0410 0x0411 0x0426 0x0414 0x0415 0x0424 0x0413
|
||||
0x0425 0x0418 0x0419 0x041a 0x041b 0x041c 0x041d 0x041e
|
||||
0x041f 0x042f 0x0420 0x0421 0x0422 0x0423 0x0416 0x0412
|
||||
0x042c 0x042b 0x0417 0x0428 0x042d 0x0429 0x0427 0x042a
|
||||
|
||||
0xe1 0xe2 0xf7 0xe7 0xe4 0xe5 0xf6 0xfa
|
||||
0xe9 0xea 0xeb 0xec 0xed 0xee 0xef 0xf0
|
||||
0xf2 0xf3 0xf4 0xf5 0xe6 0xe8 0xe3 0xfe
|
||||
0xfb 0xfd 0xff 0xf9 0xf8 0xfc 0xe0 0xf1
|
||||
0xc1 0xc2 0xd7 0xc7 0xc4 0xc5 0xd6 0xda
|
||||
0xc9 0xca 0xcb 0xcc 0xcd 0xce 0xcf 0xd0
|
||||
0x90 0x91 0x92 0x81 0x87 0xb2 0xb4 0xa7
|
||||
0xa6 0xb5 0xa1 0xa8 0xae 0xad 0xac 0x83
|
||||
0x84 0x89 0x88 0x86 0x80 0x8a 0xaf 0xb0
|
||||
0xab 0xa5 0xbb 0xb8 0xb1 0xa0 0xbe 0xb9
|
||||
0xba 0xb6 0xb7 0xaa 0xa9 0xa2 0xa4 0xbd
|
||||
0xbc 0x85 0x82 0x8d 0x8c 0x8e 0x8f 0x8b
|
||||
0xd2 0xd3 0xd4 0xd5 0xc6 0xc8 0xc3 0xde
|
||||
0xdb 0xdd 0xdf 0xd9 0xd8 0xdc 0xc0 0xd1
|
||||
0xb3 0xa3 229 197 73 105 245 213
|
||||
0x9c 0x95 0x9e 0x96 78 210 0x94 0x9a
|
||||
|
||||
0xc4 0xb3 0xda 0xbf 0xc0 0xd9 0xc3 0xb4
|
||||
0xc2 0xc1 0xc5 0xdf 0xdc 0xdb 0xdd 0xde
|
||||
0xb0 0xb1 0xb2 179 0xfe 0xf9 0xfb 61
|
||||
60 62 0xff 179 0xf8 50 0xfa 58
|
||||
0xcd 0xba 0xd5 0xf1 0xd6 0xc9 0xb8 0xb7
|
||||
0xbb 0xd4 0xd3 0xc8 0xbe 0xbd 0xbc 0xc6
|
||||
0xc7 0xcc 0xb5 0xf0 0xb6 0xb9 0xd1 0xd2
|
||||
0xcb 0xcf 0xd0 0xca 0xd8 0xd7 0xce 99
|
||||
0xee 0xa0 0xa1 0xe6 0xa4 0xa5 0xe4 0xa3
|
||||
0xe5 0xa8 0xa9 0xaa 0xab 0xac 0xad 0xae
|
||||
0xaf 0xef 0xe0 0xe1 0xe2 0xe3 0xa6 0xa2
|
||||
0xec 0xeb 0xa7 0xe8 0xed 0xe9 0xe7 0xea
|
||||
0x9e 0x80 0x81 0x96 0x84 0x85 0x94 0x83
|
||||
0x95 0x88 0x89 0x8a 0x8b 0x8c 0x8d 0x8e
|
||||
0x8f 0x9f 0x90 0x91 0x92 0x93 0x86 0x82
|
||||
0x9c 0x9b 0x87 0x98 0x9d 0x99 0x97 0x9a
|
||||
@@ -1,500 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 1997 by Matthew N. Dodd <[email protected]>
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/* Credits: Based on and part of the DPT driver for FreeBSD written and
|
||||
* maintained by Simon Shapiro <[email protected]>
|
||||
*/
|
||||
|
||||
/*
|
||||
* $Id$
|
||||
*/
|
||||
|
||||
#include "opt_dpt.h"
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/malloc.h>
|
||||
#include <sys/buf.h>
|
||||
#include <sys/proc.h>
|
||||
#include <sys/kernel.h>
|
||||
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
#include <i386/eisa/eisaconf.h>
|
||||
|
||||
#include <sys/dpt.h>
|
||||
#include <i386/eisa/dpt_eisa.h>
|
||||
|
||||
#include <machine/clock.h>
|
||||
|
||||
#include <vm/vm.h>
|
||||
#include <vm/vm_param.h>
|
||||
#include <vm/pmap.h>
|
||||
|
||||
/* Function Prototypes */
|
||||
|
||||
int dpt_eisa_probe(void);
|
||||
int dpt_eisa_attach(struct eisa_device*);
|
||||
int dpt_eisa_shutdown(int);
|
||||
|
||||
static const char *dpt_eisa_match(eisa_id_t);
|
||||
|
||||
static struct eisa_driver dpt_eisa_driver =
|
||||
{
|
||||
"dpt",
|
||||
dpt_eisa_probe,
|
||||
dpt_eisa_attach,
|
||||
dpt_eisa_shutdown,
|
||||
&dpt_unit
|
||||
};
|
||||
|
||||
DATA_SET (eisadriver_set, dpt_eisa_driver);
|
||||
|
||||
int
|
||||
dpt_eisa_probe(void)
|
||||
{
|
||||
static int already_announced = 0;
|
||||
u_int32_t io_base;
|
||||
u_int32_t irq;
|
||||
struct eisa_device *e_dev = NULL;
|
||||
dpt_conf_t *config;
|
||||
dpt_softc_t *dpt;
|
||||
int count = 0;
|
||||
|
||||
if ( !already_announced ) {
|
||||
printf("DPT: EISA SCSI HBA Driver, version %d.%d.%d\n",
|
||||
DPT_RELEASE, DPT_VERSION, DPT_PATCH);
|
||||
++already_announced;
|
||||
}
|
||||
|
||||
if ((dpt = (dpt_softc_t *) malloc(sizeof(dpt_softc_t),
|
||||
M_DEVBUF, M_NOWAIT)) == NULL) {
|
||||
printf("dpt_eisa_probe() : Failed to allocate %d bytes for a DPT softc\n", sizeof(dpt_softc_t));
|
||||
return -1;
|
||||
}
|
||||
|
||||
bzero(dpt, sizeof(dpt_softc_t));
|
||||
|
||||
TAILQ_INIT(&dpt->free_ccbs);
|
||||
TAILQ_INIT(&dpt->waiting_ccbs);
|
||||
TAILQ_INIT(&dpt->submitted_ccbs);
|
||||
TAILQ_INIT(&dpt->completed_ccbs);
|
||||
|
||||
dpt->queue_status = DPT_QUEUES_NONE_ACTIVE;
|
||||
dpt->commands_processed = 0;
|
||||
dpt->handle_interrupts = 0;
|
||||
dpt->v_membase = NULL;
|
||||
dpt->p_membase = NULL;
|
||||
|
||||
dpt->unit = -1;
|
||||
|
||||
while ((e_dev = eisa_match_dev(e_dev, dpt_eisa_match))) {
|
||||
io_base = (e_dev->ioconf.slot * EISA_SLOT_SIZE)
|
||||
+ DPT_EISA_SLOT_OFFSET;
|
||||
|
||||
eisa_add_iospace(e_dev, io_base,
|
||||
DPT_EISA_IOSIZE, RESVADDR_NONE);
|
||||
|
||||
dpt->io_base = io_base;
|
||||
|
||||
if ((config = dpt_get_conf(dpt, 0xc1, 7,
|
||||
sizeof(dpt_conf_t), 1)) == NULL) {
|
||||
#ifdef DPT_DEBUG_ERROR
|
||||
printf("eisa0:%d dpt_eisa_probe() : Failed to get board configuration.\n",
|
||||
e_dev->ioconf.slot);
|
||||
#endif
|
||||
continue;
|
||||
}
|
||||
|
||||
irq = config->IRQ;
|
||||
|
||||
eisa_add_intr(e_dev, irq);
|
||||
eisa_registerdev(e_dev, &dpt_eisa_driver);
|
||||
|
||||
count++;
|
||||
|
||||
}
|
||||
|
||||
free(dpt, M_DEVBUF);
|
||||
return count;
|
||||
}
|
||||
|
||||
int
|
||||
dpt_eisa_attach(e_dev)
|
||||
struct eisa_device *e_dev;
|
||||
{
|
||||
int result;
|
||||
int ndx;
|
||||
|
||||
dpt_conf_t *config;
|
||||
dpt_softc_t *dpt;
|
||||
|
||||
int unit = e_dev->unit;
|
||||
int irq;
|
||||
resvaddr_t *io_space;
|
||||
|
||||
if (TAILQ_FIRST(&e_dev->ioconf.irqs) == NULL) {
|
||||
#ifdef DPT_DEBUG_ERROR
|
||||
printf("dpt%d: Can't retrieve irq from EISA config struct.\n",
|
||||
unit);
|
||||
#endif
|
||||
return -1;
|
||||
}
|
||||
|
||||
irq = TAILQ_FIRST(&e_dev->ioconf.irqs)->irq_no;
|
||||
io_space = e_dev->ioconf.ioaddrs.lh_first;
|
||||
|
||||
if (!io_space) {
|
||||
#ifdef DPT_DEBUG_ERROR
|
||||
printf("dpt%d: No I/O space?!\n", unit);
|
||||
#endif
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ( dpt_controllers_present >= DPT_MAX_ADAPTERS ){
|
||||
printf("dpt%d: More than %d Adapters found! Adapter rejected\n",
|
||||
unit, DPT_MAX_ADAPTERS);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ((dpt = (dpt_softc_t *) malloc(sizeof(dpt_softc_t),
|
||||
M_DEVBUF, M_NOWAIT)) == NULL) {
|
||||
printf("dpt%d: Failed to allocate %d bytes for a DPT softc\n",
|
||||
unit, sizeof(dpt_softc_t));
|
||||
return -1;
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialize the queues. See dpt.h for details. We do this here,
|
||||
* as we may get hit with interrupts at any moment and we want to
|
||||
* have a minimal structure in place to handle them. We also want to
|
||||
* register interrupts correctly. To do so, we need a valid dpt
|
||||
* structure. To have that, we need this minimal setup here.
|
||||
*/
|
||||
|
||||
bzero(dpt, sizeof(dpt_softc_t));
|
||||
|
||||
TAILQ_INIT(&dpt->free_ccbs);
|
||||
TAILQ_INIT(&dpt->waiting_ccbs);
|
||||
TAILQ_INIT(&dpt->submitted_ccbs);
|
||||
TAILQ_INIT(&dpt->completed_ccbs);
|
||||
|
||||
if (TAILQ_EMPTY(&dpt_softc_list)) {
|
||||
TAILQ_INIT(&dpt_softc_list);
|
||||
}
|
||||
|
||||
TAILQ_INSERT_TAIL(&dpt_softc_list, dpt, links);
|
||||
dpt->queue_status = DPT_QUEUES_NONE_ACTIVE;
|
||||
dpt->commands_processed = 0;
|
||||
|
||||
#ifdef DPT_MEASURE_PERFORMANCE
|
||||
/* Zero out all command counters */
|
||||
bzero((void *)&dpt->performance, sizeof(dpt_perf_t));
|
||||
#endif /* DPT_MEASURE_PERFORMANCE */
|
||||
|
||||
dpt->handle_interrupts = 0; /*
|
||||
* Do not set to 1 until all
|
||||
* initialization is done
|
||||
*/
|
||||
dpt->v_membase = NULL;
|
||||
dpt->p_membase = NULL;
|
||||
|
||||
dpt->unit = unit;
|
||||
dpt->io_base = (e_dev->ioconf.slot * EISA_SLOT_SIZE)
|
||||
+ DPT_EISA_SLOT_OFFSET;
|
||||
|
||||
eisa_reg_start(e_dev);
|
||||
|
||||
if (eisa_reg_iospace(e_dev, io_space)) {
|
||||
#ifdef DPT_DEBUG_ERROR
|
||||
printf("dpt%d: eisa_reg_iospace() failed.\n", unit);
|
||||
#endif
|
||||
free(dpt, M_DEVBUF);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* reset the card? */
|
||||
|
||||
/* If the DPT is mapped as an IDE controller, let it be IDE controller */
|
||||
if (dpt->io_base == ISA_PRIMARY_WD_ADDRESS) {
|
||||
#ifdef DPT_DEBUG_WARN
|
||||
printf("dpt%d: Mapped as an IDE controller. "
|
||||
"Disabling SCSI setup\n", unit);
|
||||
#endif
|
||||
free(dpt, M_DEVBUF);
|
||||
return -1;
|
||||
} else {
|
||||
if ((config = dpt_get_conf(dpt, 0xc1, 7,
|
||||
sizeof(dpt_conf_t), 1)) == NULL) {
|
||||
#ifdef DPT_DEBUG_ERROR
|
||||
printf("dpt%d: Failed to get board configuration (%x)\n",
|
||||
unit, BaseRegister(dpt));
|
||||
#endif
|
||||
free(dpt, M_DEVBUF);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
if(eisa_reg_intr(e_dev, irq, dpt_intr, (void *)dpt, &cam_imask,
|
||||
/* shared == */ config->IRQ_TR)) {
|
||||
#ifdef DPT_DEBUG_ERROR
|
||||
printf("dpt%d: eisa_reg_intr() failed.\n", unit);
|
||||
#endif
|
||||
free(dpt, M_DEVBUF);
|
||||
return -1;
|
||||
}
|
||||
eisa_reg_end(e_dev);
|
||||
|
||||
/* Enable our interrupt handler. */
|
||||
if (eisa_enable_intr(e_dev, irq)) {
|
||||
#ifdef DPT_DEBUG_ERROR
|
||||
printf("dpt%d: eisa_enable_intr() failed.\n", unit);
|
||||
#endif
|
||||
free(dpt, M_DEVBUF);
|
||||
eisa_release_intr(e_dev, irq, dpt_intr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
dpt->max_id = config->MAX_ID;
|
||||
dpt->max_lun = config->MAX_LUN;
|
||||
dpt->irq = config->IRQ;
|
||||
dpt->channels = config->MAX_CHAN;
|
||||
dpt->dma_channel = (8 - config->DMA_channel) & 7;
|
||||
|
||||
#ifdef DPT_DEBUG_SETUP
|
||||
printf("dpt%d: max_id = %d, max_chan = %d, max_lun = %d\n",
|
||||
dpt->unit, dpt->max_id, dpt->channels, dpt->max_lun);
|
||||
#endif
|
||||
|
||||
if (result = dpt_setup(dpt, config)) {
|
||||
free(config, M_TEMP);
|
||||
free(dpt, M_DEVBUF);
|
||||
printf("dpt%d: dpt_setup failed (%d). Driver Disabled :-(\n",
|
||||
dpt->unit, result);
|
||||
} else {
|
||||
/* clean up the informational data, and display */
|
||||
char clean_vendor[9];
|
||||
char clean_model[17];
|
||||
char clean_firmware[5];
|
||||
char clean_protocol[5];
|
||||
char clean_other[7];
|
||||
|
||||
int ndx;
|
||||
|
||||
strncpy(clean_other, dpt->board_data.otherData, 8);
|
||||
clean_other[6] = '\0';
|
||||
for (ndx = 5; ndx >= 0; ndx--) {
|
||||
if (clean_other[ndx] == ' ') {
|
||||
clean_other[ndx] = '\0';
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
strncpy(dpt->board_data.otherData, clean_other, 6);
|
||||
|
||||
strncpy(clean_vendor, dpt->board_data.vendor, 8);
|
||||
clean_vendor[8] = '\0';
|
||||
|
||||
for (ndx = 7; ndx >= 0; ndx--) {
|
||||
if (clean_vendor[ndx] == ' ') {
|
||||
clean_vendor[ndx] = '\0';
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
strncpy(dpt->board_data.vendor, clean_vendor, 8);
|
||||
|
||||
strncpy(clean_model, dpt->board_data.modelNum, 16);
|
||||
clean_model[16] = '\0';
|
||||
|
||||
for (ndx = 15; ndx >= 0; ndx--) {
|
||||
if (clean_model[ndx] == ' ') {
|
||||
clean_model[ndx] = '\0';
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
strncpy(dpt->board_data.modelNum, clean_model, 16);
|
||||
|
||||
strncpy(clean_firmware, dpt->board_data.firmware, 4);
|
||||
clean_firmware[4] = '\0';
|
||||
|
||||
for (ndx = 3; ndx >= 0; ndx--) {
|
||||
if (clean_firmware[ndx] == ' ')
|
||||
clean_firmware[ndx] = '\0';
|
||||
else
|
||||
break;
|
||||
}
|
||||
|
||||
strncpy(dpt->board_data.firmware, clean_firmware, 4);
|
||||
|
||||
strncpy(clean_protocol, dpt->board_data.protocol, 4);
|
||||
clean_protocol[4] = '\0';
|
||||
|
||||
for (ndx = 3; ndx >= 0; ndx--) {
|
||||
if (clean_protocol[ndx] == ' ')
|
||||
clean_protocol[ndx] = '\0';
|
||||
else
|
||||
break;
|
||||
}
|
||||
|
||||
strncpy(dpt->board_data.protocol, clean_protocol, 4);
|
||||
|
||||
dpt_detect_cache(dpt);
|
||||
|
||||
printf("dpt%d: %s type %x, model %s firmware %s, Protocol %s \n"
|
||||
" on port %x with %dMB %s cache. LED = %s\n",
|
||||
dpt->unit, clean_vendor, dpt->board_data.deviceType,
|
||||
clean_model, clean_firmware, clean_protocol, dpt->io_base,
|
||||
dpt->cache_size,
|
||||
(dpt->cache_type == DPT_NO_CACHE)
|
||||
? "Disabled"
|
||||
: (dpt->cache_type == DPT_CACHE_WRITETHROUGH)
|
||||
? "Write-Through"
|
||||
: "Write-Back",
|
||||
i2bin(dpt_blinking_led(dpt), 8));
|
||||
|
||||
printf("dpt%d: Enabled Options:\n", dpt->unit);
|
||||
|
||||
#ifdef DPT_VERIFY_HINTR
|
||||
printf(" Verify Lost Transactions\n");
|
||||
#endif
|
||||
#ifdef DPT_RESTRICTED_FREELIST
|
||||
printf(" Restrict the Freelist Size\n");
|
||||
#endif
|
||||
#ifdef DPT_TRACK_CCB_STATES
|
||||
printf(" Precisely Track State Transitions\n");
|
||||
#endif
|
||||
#ifdef DPT_MEASURE_PERFORMANCE
|
||||
printf(" Collect Metrics\n");
|
||||
#endif
|
||||
#ifdef DPT_FREELIST_IS_STACK
|
||||
printf(" Optimize CPU Cache\n");
|
||||
#endif
|
||||
#ifdef DPT_HANDLE_TIMEOUTS
|
||||
printf(" Handle Timeouts\n");
|
||||
#endif
|
||||
#ifdef DPT_ALLOW_MEMIO
|
||||
printf(" Allow I/O to be Memeory Mapped\n");
|
||||
#endif
|
||||
#ifdef DPT_HINTR_CHECK_SOFTC
|
||||
printf(" Validate SoftC at Interrupt\n");
|
||||
#endif
|
||||
|
||||
/* register shutdown handlers */
|
||||
result = at_shutdown((bootlist_fn)dpt_shutdown, (void *)dpt,
|
||||
SHUTDOWN_POST_SYNC);
|
||||
switch ( result ) {
|
||||
case 0:
|
||||
#ifdef DPT_DEBUG_SHUTDOWN
|
||||
printf("dpt%d: Shutdown handler registered\n", dpt->unit);
|
||||
#endif
|
||||
break;
|
||||
default:
|
||||
#ifdef DPT_DEBUG_WARN
|
||||
printf("dpt%d: Failed to register shutdown handler (%d)\n",
|
||||
dpt->unit, result);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
|
||||
dpt_attach(dpt);
|
||||
}
|
||||
|
||||
++dpt_controllers_present;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
dpt_eisa_shutdown(foo)
|
||||
int foo;
|
||||
{
|
||||
#ifdef DPT_DEBUG_WARN
|
||||
printf("dpt_pci_shutdown(%x)\n", foo);
|
||||
#endif
|
||||
return (0);
|
||||
}
|
||||
|
||||
static const char *
|
||||
dpt_eisa_match(type)
|
||||
eisa_id_t type;
|
||||
{
|
||||
switch (type) {
|
||||
case DPT_EISA_DPT2402 :
|
||||
return ("DPT PM2012A/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTA401 :
|
||||
return ("DPT PM2012B/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTA402 :
|
||||
return ("DPT PM2012B2/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTA410 :
|
||||
return ("DPT PM2x22A/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTA411 :
|
||||
return ("DPT Spectre");
|
||||
break;
|
||||
case DPT_EISA_DPTA412 :
|
||||
return ("DPT PM2021A/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTA420 :
|
||||
return ("DPT Smart Cache IV (PM2042)");
|
||||
break;
|
||||
case DPT_EISA_DPTA501 :
|
||||
return ("DPT PM2012B1/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTA502 :
|
||||
return ("DPT PM2012Bx/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTA701 :
|
||||
return ("DPT PM2011B1/9X");
|
||||
break;
|
||||
case DPT_EISA_DPTBC01 :
|
||||
return ("DPT PM3011/7X ESDI");
|
||||
break;
|
||||
case DPT_EISA_NEC8200 :
|
||||
return ("NEC EATA SCSI");
|
||||
break;
|
||||
case DPT_EISA_ATT2408 :
|
||||
return ("ATT EATA SCSI");
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
@@ -1,56 +0,0 @@
|
||||
/**
|
||||
* Copyright (c) 1997 by Matthew N. Dodd <[email protected]>
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/* Credits: Based on and part of the DPT driver for FreeBSD written and
|
||||
* maintained by Simon Shapiro <[email protected]>
|
||||
*/
|
||||
|
||||
/*
|
||||
* $Id: dpt_eisa.h,v 1.1 1998/03/10 21:31:06 ShimonR Exp ShimonR $
|
||||
*/
|
||||
|
||||
#define DPT_EISA_SLOT_OFFSET 0xc88 /* 8 */
|
||||
#define DPT_EISA_IOSIZE sizeof(eata_reg_t)
|
||||
|
||||
#define ISA_PRIMARY_WD_ADDRESS 0x1f8
|
||||
|
||||
#define DPT_EISA_DPT2402 0x12142402
|
||||
#define DPT_EISA_DPTA401 0x1214A401
|
||||
#define DPT_EISA_DPTA402 0x1214A402
|
||||
#define DPT_EISA_DPTA410 0x1214A410
|
||||
#define DPT_EISA_DPTA411 0x1214A411
|
||||
#define DPT_EISA_DPTA412 0x1214A412
|
||||
#define DPT_EISA_DPTA420 0x1214A420
|
||||
#define DPT_EISA_DPTA501 0x1214A501
|
||||
#define DPT_EISA_DPTA502 0x1214A502
|
||||
#define DPT_EISA_DPTA701 0x1214A701
|
||||
#define DPT_EISA_DPTBC01 0x1214BC01
|
||||
#define DPT_EISA_NEC8200 0x12148200
|
||||
#define DPT_EISA_ATT2408 0x12142408
|
||||
|
||||
@@ -1,31 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 Justin Gibbs.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id$
|
||||
*/
|
||||
|
||||
#ifndef _I386_BUS_MEMIO_H_
|
||||
#define _I386_BUS_MEMIO_H_
|
||||
#endif /* _I386_BUS_MEMIO_H_ */
|
||||
@@ -1,31 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 Justin Gibbs.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id$
|
||||
*/
|
||||
|
||||
#ifndef _I386_BUS_PIO_H_
|
||||
#define _I386_BUS_PIO_H_
|
||||
#endif /* _I386_BUS_PIO_H_ */
|
||||
-1013
File diff suppressed because it is too large.
Load diff
@@ -1,140 +0,0 @@
|
||||
/*
|
||||
* Include file for PCMCIA user process interface
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (c) 1995 Andrew McRae. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef _PCCARD_CARDINFO_H_
|
||||
#define _PCCARD_CARDINFO_H_
|
||||
|
||||
#ifndef KERNEL
|
||||
#include <sys/types.h>
|
||||
#endif
|
||||
#include <sys/ioccom.h>
|
||||
|
||||
#define PIOCGSTATE _IOR('P', 1, struct slotstate) /* Get slot state */
|
||||
#define PIOCGMEM _IOWR('P', 2, struct mem_desc) /* Get memory map */
|
||||
#define PIOCSMEM _IOW('P', 3, struct mem_desc) /* Set memory map */
|
||||
#define PIOCGIO _IOWR('P', 4, struct io_desc) /* Get I/O map */
|
||||
#define PIOCSIO _IOW('P', 5, struct io_desc) /* Set I/O map */
|
||||
#define PIOCSDRV _IOW('P', 6, struct dev_desc) /* Set driver */
|
||||
#define PIOCRWFLAG _IOW('P', 7, int) /* Set flags for drv use */
|
||||
#define PIOCRWMEM _IOWR('P', 8, unsigned long) /* Set mem for drv use */
|
||||
#define PIOCSPOW _IOW('P', 9, struct power) /* Set power structure */
|
||||
/*
|
||||
* Debug codes.
|
||||
*/
|
||||
#define PIOCGREG _IOWR('P',100, struct pcic_reg) /* get reg */
|
||||
#define PIOCSREG _IOW('P', 101, struct pcic_reg) /* Set reg */
|
||||
|
||||
/*
|
||||
* Slot states for PIOCGSTATE
|
||||
*/
|
||||
enum cardstate { noslot, empty, suspend, filled };
|
||||
|
||||
/*
|
||||
* Descriptor structure for memory map.
|
||||
*/
|
||||
struct mem_desc {
|
||||
int window; /* Memory map window number (0-4) */
|
||||
int flags; /* Flags - see below */
|
||||
caddr_t start; /* System memory start */
|
||||
int size; /* Size of memory area */
|
||||
unsigned long card; /* Card memory address */
|
||||
};
|
||||
|
||||
#define MDF_16BITS 0x01 /* Memory is 16 bits wide */
|
||||
#define MDF_ZEROWS 0x02 /* Set no wait states for memory */
|
||||
#define MDF_WS0 0x04 /* Wait state flags */
|
||||
#define MDF_WS1 0x08
|
||||
#define MDF_ATTR 0x10 /* Memory is attribute memory */
|
||||
#define MDF_WP 0x20 /* Write protect memory */
|
||||
#define MDF_ACTIVE 0x40 /* Context active (read-only) */
|
||||
|
||||
/*
|
||||
* Descriptor structure for I/O map
|
||||
*/
|
||||
struct io_desc {
|
||||
int window; /* I/O map number (0-1) */
|
||||
int flags; /* Flags - see below */
|
||||
int start; /* I/O port start */
|
||||
int size; /* Number of port addresses */
|
||||
};
|
||||
|
||||
#define IODF_WS 0x01 /* Set wait states for 16 bit I/O access */
|
||||
#define IODF_16BIT 0x02 /* I/O access are 16 bit */
|
||||
#define IODF_CS16 0x04 /* Allow card selection of 16 bit access */
|
||||
#define IODF_ZEROWS 0x08 /* No wait states for 8 bit I/O */
|
||||
#define IODF_ACTIVE 0x10 /* Context active (read-only) */
|
||||
|
||||
/*
|
||||
* Device descriptor for allocation of driver.
|
||||
*/
|
||||
struct dev_desc {
|
||||
char name[16]; /* Driver name */
|
||||
int unit; /* Driver unit number */
|
||||
unsigned long mem; /* Memory address of driver */
|
||||
int memsize; /* Memory size (if used) */
|
||||
int iobase; /* base of I/O ports */
|
||||
int irqmask; /* Interrupt number(s) to allocate */
|
||||
int flags; /* Device flags */
|
||||
u_char misc[128]; /* For any random info */
|
||||
};
|
||||
|
||||
struct pcic_reg {
|
||||
unsigned char reg;
|
||||
unsigned char value;
|
||||
};
|
||||
|
||||
/*
|
||||
* Slot information. Used to read current status of slot.
|
||||
*/
|
||||
struct slotstate {
|
||||
enum cardstate state; /* Current state of slot */
|
||||
int maxmem; /* Max allowed memory windows */
|
||||
int maxio; /* Max allowed I/O windows */
|
||||
int irqs; /* Bitmap of IRQs allowed */
|
||||
int flags; /* Capability flags */
|
||||
};
|
||||
|
||||
/*
|
||||
* The power values are in volts * 10, e.g. 5V is 50, 3.3V is 33.
|
||||
*/
|
||||
struct power {
|
||||
int vcc;
|
||||
int vpp;
|
||||
};
|
||||
|
||||
/*
|
||||
* Other system limits
|
||||
*/
|
||||
#define MAXSLOT 16
|
||||
#define NUM_MEM_WINDOWS 10
|
||||
#define NUM_IO_WINDOWS 6
|
||||
#define CARD_DEVICE "/dev/card%d" /* String for sprintf */
|
||||
|
||||
#endif /* !_PCCARD_CARDINFO_H_ */
|
||||
+11
-3
@@ -35,10 +35,18 @@
|
||||
#
|
||||
|
||||
if [ $# -eq 0 ]; then
|
||||
echo 'usage: shar file ...'
|
||||
exit 1
|
||||
echo 'usage: shar file ...' 1>&2
|
||||
exit 64 # EX_USAGE
|
||||
fi
|
||||
|
||||
for i
|
||||
do
|
||||
if [ ! \( -d $i -o -r $i \) ]; then
|
||||
echo "$i inaccessible or not exist" 1>&2
|
||||
exit 66 # EX_NOINPUT
|
||||
fi
|
||||
done
|
||||
|
||||
cat << EOF
|
||||
# This is a shell archive. Save it in a file, remove anything before
|
||||
# this line, and then unpack it by entering "sh file". Note, it may
|
||||
@@ -64,7 +72,7 @@ do
|
||||
else
|
||||
echo "echo x - $i"
|
||||
echo "sed 's/^X//' >$i << 'END-of-$i'"
|
||||
sed 's/^/X/' $i
|
||||
sed 's/^/X/' $i || exit
|
||||
echo "END-of-$i"
|
||||
fi
|
||||
done
|
||||
|
||||
@@ -1,5 +0,0 @@
|
||||
# $Id: Makefile,v 1.2 1998/01/21 07:46:46 ShimonR Exp ShimonR $
|
||||
|
||||
SUBDIR= dpt_ctlinfo dpt_ctls dpt_dm dpt_led dpt_sig dpt_softc dpt_sysinfo
|
||||
|
||||
.include <bsd.subdir.mk>
|
||||
@@ -1,12 +0,0 @@
|
||||
# @(#)Makefile 8.1 (Berkeley) 5/31/93
|
||||
# $Id: Makefile,v 1.1 1998/01/22 23:32:27 ShimonR Exp ShimonR $
|
||||
|
||||
PROG= dpt_ctlinfo
|
||||
SRCS= dpt_ctlinfo.c
|
||||
|
||||
CFLAGS+=-Wall -I../../../sys -I/usr/src/sys
|
||||
BINMODE=500
|
||||
BINOWN= root
|
||||
MAN8= dpt_ctlinfo.8
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,3 +0,0 @@
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
@@ -1,121 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 by Simon Shapiro
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
/* dpt_ctlinfo.c: Dunp a DPT HBA Information Block */
|
||||
|
||||
#ident "$Id: dpt_ctlinfo.c,v 1.1 1998/01/22 23:32:27 ShimonR Exp ShimonR $"
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
#define DPT_MEASURE_PERFORMANCE
|
||||
|
||||
#include <sys/dpt.h>
|
||||
|
||||
|
||||
int
|
||||
main(int argc, char **argv, char **argp)
|
||||
{
|
||||
eata_pt_t pass_thru;
|
||||
dpt_compat_ha_t compat_softc;
|
||||
|
||||
int result;
|
||||
int fd;
|
||||
int ndx;
|
||||
|
||||
if ( (fd = open(argv[1], O_RDWR, S_IRUSR | S_IWUSR)) == -1 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to open \"%s\" - %s\n",
|
||||
argv[0], argv[1], strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
pass_thru.eataID[0] = 'E';
|
||||
pass_thru.eataID[1] = 'A';
|
||||
pass_thru.eataID[2] = 'T';
|
||||
pass_thru.eataID[3] = 'A';
|
||||
pass_thru.command = DPT_CTRLINFO;
|
||||
pass_thru.command_buffer = (u_int8_t *)&compat_softc;
|
||||
|
||||
if ( (result = ioctl(fd, DPT_IOCTL_SEND, &pass_thru)) != 0 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to send IOCTL %x - %s\n",
|
||||
argv[0], DPT_IOCTL_SEND,
|
||||
strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%x:", compat_softc.ha_state);
|
||||
|
||||
for (ndx = 0; ndx < MAX_CHANNELS; ndx++)
|
||||
(void)fprintf(stdout, (ndx == (MAX_CHANNELS - 1)) ? "%d:" : "%d,",
|
||||
compat_softc.ha_id[ndx]);
|
||||
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_vect);
|
||||
(void)fprintf(stdout, "%x:", compat_softc.ha_base);
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_max_jobs);
|
||||
|
||||
switch (compat_softc.ha_cache) {
|
||||
case DPT_NO_CACHE:
|
||||
(void)fprintf(stdout, "No Cache:");
|
||||
break;
|
||||
case DPT_CACHE_WRITETHROUGH:
|
||||
(void)fprintf(stdout, "WriteThrough:");
|
||||
break;
|
||||
case DPT_CACHE_WRITEBACK:
|
||||
(void)fprintf(stdout, "WriteBack:");
|
||||
break;
|
||||
default:
|
||||
(void)fprintf(stdout, "UnKnown (%d):", compat_softc.ha_cache);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_cachesize);
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_nbus);
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_ntargets);
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_nluns);
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_tshift);
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_bshift);
|
||||
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_npend);
|
||||
(void)fprintf(stdout, "%d:", compat_softc.ha_active_jobs);
|
||||
|
||||
(void)fprintf(stdout, "%s\n", compat_softc.ha_fw_version);
|
||||
|
||||
|
||||
|
||||
return(0);
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
# @(#)Makefile 8.1 (Berkeley) 5/31/93
|
||||
# $Id: Makefile,v 1.1 1998/01/22 22:07:22 ShimonR Exp ShimonR $
|
||||
|
||||
PROG= dpt_ctls
|
||||
SRCS= dpt_ctls.c
|
||||
|
||||
CFLAGS+=-Wall -I../../../sys -I/usr/src/sys
|
||||
BINMODE=500
|
||||
BINOWN= root
|
||||
MAN8= dpt_ctls.8
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,3 +0,0 @@
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
@@ -1,80 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 by Simon Shapiro
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
/* dpt_ctls.c: Dunp a the number of configured DPT HBAs */
|
||||
|
||||
#ident "$Id: dpt_ctls.c,v 1.1 1998/01/22 22:07:22 ShimonR Exp ShimonR $"
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
#include <sys/dpt.h>
|
||||
|
||||
int
|
||||
main(int argc, char **argv, char **argp)
|
||||
{
|
||||
eata_pt_t pass_thru;
|
||||
int controllers_present;
|
||||
|
||||
int result;
|
||||
int fd;
|
||||
|
||||
if ( (fd = open(argv[1], O_RDWR, S_IRUSR | S_IWUSR)) == -1 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to open \"%s\" - %s\n",
|
||||
argv[0], argv[1], strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
pass_thru.eataID[0] = 'E';
|
||||
pass_thru.eataID[1] = 'A';
|
||||
pass_thru.eataID[2] = 'T';
|
||||
pass_thru.eataID[3] = 'A';
|
||||
pass_thru.command = DPT_NUMCTRLS;
|
||||
pass_thru.command_buffer = (u_int8_t *)&controllers_present;
|
||||
|
||||
if ( (result = ioctl(fd, DPT_IOCTL_SEND, &pass_thru)) != 0 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to send IOCTL %x - %s\n",
|
||||
argv[0], DPT_IOCTL_SEND,
|
||||
strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%d\n", controllers_present);
|
||||
return(0);
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
# @(#)Makefile 8.1 (Berkeley) 5/31/93
|
||||
# $Id: Makefile,v 1.4 1998/01/21 17:38:32 ShimonR Exp ShimonR $
|
||||
|
||||
PROG= dpt_dm
|
||||
SRCS= dpt_dm.c
|
||||
|
||||
CFLAGS+=-Wall -I../../../sys -I/usr/src/sys
|
||||
BINMODE=500
|
||||
BINOWN= root
|
||||
MAN8= dpt_dm.8
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,6 +0,0 @@
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
@@ -1,391 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 by Simon Shapiro
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
/* dpt_dm.c: Dump a DPT metrics structure */
|
||||
|
||||
#ident "$Id: dpt_dm.c,v 1.8 1998/01/21 17:38:32 ShimonR Exp ShimonR $"
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
#define DPT_MEASURE_PERFORMANCE
|
||||
|
||||
#include <sys/dpt.h>
|
||||
|
||||
char *
|
||||
scsi_cmd_name(u_int8_t cmd)
|
||||
{
|
||||
switch (cmd) {
|
||||
case 0x40:
|
||||
return ("Change Definition [7.1]");
|
||||
break;
|
||||
case 0x39:
|
||||
return ("Compare [7,2]");
|
||||
break;
|
||||
case 0x18:
|
||||
return ("Copy [7.3]");
|
||||
break;
|
||||
case 0x3a:
|
||||
return ("Copy and Verify [7.4]");
|
||||
break;
|
||||
case 0x04:
|
||||
return ("Format Unit [6.1.1]");
|
||||
break;
|
||||
case 0x12:
|
||||
return ("Inquiry [7.5]");
|
||||
break;
|
||||
case 0x36:
|
||||
return ("lock/Unlock Cache [6.1.2]");
|
||||
break;
|
||||
case 0x4c:
|
||||
return ("Log Select [7.6]");
|
||||
break;
|
||||
case 0x4d:
|
||||
return ("Log Sense [7.7]");
|
||||
break;
|
||||
case 0x15:
|
||||
return ("Mode select (6) [7.8]");
|
||||
break;
|
||||
case 0x55:
|
||||
return ("Mode Select (10) [7.9]");
|
||||
break;
|
||||
case 0x1a:
|
||||
return ("Mode Sense (6) [7.10]");
|
||||
break;
|
||||
case 0x5a:
|
||||
return ("Mode Sense (10) [7.11]");
|
||||
break;
|
||||
case 0xa7:
|
||||
return ("Move Medium Attached [SMC]");
|
||||
break;
|
||||
case 0x5e:
|
||||
return ("Persistent Reserve In [7.12]");
|
||||
break;
|
||||
case 0x5f:
|
||||
return ("Persistent Reserve Out [7.13]");
|
||||
break;
|
||||
case 0x1e:
|
||||
return ("Prevent/Allow Medium Removal [7.14]");
|
||||
break;
|
||||
case 0x08:
|
||||
return ("Read, Receive (6) [6.1.5]");
|
||||
break;
|
||||
case 0x28:
|
||||
return ("Read (10) [6.1.5]");
|
||||
break;
|
||||
case 0xa8:
|
||||
return ("Read (12) [6.1.5]");
|
||||
break;
|
||||
case 0x3c:
|
||||
return ("Read Buffer [7.15]");
|
||||
break;
|
||||
case 0x25:
|
||||
return ("Read Capacity [6.1.6]");
|
||||
break;
|
||||
case 0x37:
|
||||
return ("Read Defect Data (10) [6.1.7]");
|
||||
break;
|
||||
case 0xb7:
|
||||
return ("Read Defect Data (12) [6.2.5]");
|
||||
break;
|
||||
case 0xb4:
|
||||
return ("Read Element Status Attached [SMC]");
|
||||
break;
|
||||
case 0x3e:
|
||||
return ("Read Long [6.1.8]");
|
||||
break;
|
||||
case 0x07:
|
||||
return ("Reassign Blocks [6.1.9]");
|
||||
break;
|
||||
case 0x81:
|
||||
return ("Rebuild [6.1.10]");
|
||||
break;
|
||||
case 0x1c:
|
||||
return ("Receive Diagnostics Result [7.16]");
|
||||
break;
|
||||
case 0x82:
|
||||
return ("Regenerate [6.1.11]");
|
||||
break;
|
||||
case 0x17:
|
||||
return ("Release(6) [7.17]");
|
||||
break;
|
||||
case 0x57:
|
||||
return ("Release(10) [7.18]");
|
||||
break;
|
||||
case 0xa0:
|
||||
return ("Report LUNs [7.19]");
|
||||
break;
|
||||
case 0x03:
|
||||
return ("Request Sense [7.20]");
|
||||
break;
|
||||
case 0x16:
|
||||
return ("Resereve (6) [7.21]");
|
||||
break;
|
||||
case 0x56:
|
||||
return ("Reserve(10) [7.22]");
|
||||
break;
|
||||
case 0x2b:
|
||||
return ("Reserve(10) [6.1.12]");
|
||||
break;
|
||||
case 0x1d:
|
||||
return ("Send Disagnostics [7.23]");
|
||||
break;
|
||||
case 0x33:
|
||||
return ("Set Limit (10) [6.1.13]");
|
||||
break;
|
||||
case 0xb3:
|
||||
return ("Set Limit (12) [6.2.8]");
|
||||
break;
|
||||
case 0x1b:
|
||||
return ("Start/Stop Unit [6.1.14]");
|
||||
break;
|
||||
case 0x35:
|
||||
return ("Synchronize Cache [6.1.15]");
|
||||
break;
|
||||
case 0x00:
|
||||
return ("Test Unit Ready [7.24]");
|
||||
break;
|
||||
case 0x3d:
|
||||
return ("Update Block (6.2.9");
|
||||
break;
|
||||
case 0x2f:
|
||||
return ("Verify (10) [6.1.16, 6.2.10]");
|
||||
break;
|
||||
case 0xaf:
|
||||
return ("Verify (12) [6.2.11]");
|
||||
break;
|
||||
case 0x0a:
|
||||
return ("Write, Send (6) [6.1.17, 9.2]");
|
||||
break;
|
||||
case 0x2a:
|
||||
return ("Write (10) [6.1.18]");
|
||||
break;
|
||||
case 0xaa:
|
||||
return ("Write (12) [6.2.13]");
|
||||
break;
|
||||
case 0x2e:
|
||||
return ("Write and Verify (10) [6.1.19, 6.2.14]");
|
||||
break;
|
||||
case 0xae:
|
||||
return ("Write and Verify (12) [6.1.19, 6.2.15]");
|
||||
break;
|
||||
case 0x03b:
|
||||
return ("Write Buffer [7.25]");
|
||||
break;
|
||||
case 0x03f:
|
||||
return ("Write Long [6.1.20]");
|
||||
break;
|
||||
case 0x041:
|
||||
return ("Write Same [6.1.21]");
|
||||
break;
|
||||
case 0x052:
|
||||
return ("XD Read [6.1.22]");
|
||||
break;
|
||||
case 0x050:
|
||||
return ("XD Write [6.1.22]");
|
||||
break;
|
||||
case 0x080:
|
||||
return ("XD Write Extended [6.1.22]");
|
||||
break;
|
||||
case 0x051:
|
||||
return ("XO Write [6.1.22]");
|
||||
break;
|
||||
default:
|
||||
return ("Unknown SCSI Command");
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
main(int argc, char **argv, char **argp)
|
||||
{
|
||||
dpt_perf_t metrics;
|
||||
int result;
|
||||
int fd;
|
||||
int ndx;
|
||||
|
||||
if ( (fd = open(argv[1], O_RDWR, S_IRUSR | S_IWUSR)) == -1 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to open \"%s\" - %s\n",
|
||||
argv[0], argv[1], strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if ( (result = ioctl(fd, DPT_IOCTL_INTERNAL_METRICS, &metrics)) != 0 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to send IOCTL %x - %s\n",
|
||||
argv[0], DPT_IOCTL_INTERNAL_METRICS,
|
||||
strerror(errno));
|
||||
exit(2);
|
||||
}
|
||||
|
||||
/* Interrupt related measurements */
|
||||
(void)fprintf(stdout, "Interrupts:%d:%d:%d:%d\n\nCommands:\n",
|
||||
metrics.aborted_interrupts,
|
||||
metrics.spurious_interrupts,
|
||||
metrics.min_intr_time,
|
||||
metrics.max_intr_time);
|
||||
|
||||
/* SCSI Commands, can be no more than 256 of them */
|
||||
for (ndx = 0; ndx < 256; ndx++) {
|
||||
if (metrics.command_count[ndx] != 0) {
|
||||
(void)fprintf(stdout, "%d:%s:%d:%d:%d\n",
|
||||
ndx,
|
||||
scsi_cmd_name((u_int8_t)ndx),
|
||||
metrics.command_count[ndx],
|
||||
metrics.min_command_time[ndx],
|
||||
metrics.max_command_time[ndx]);
|
||||
}
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "\nREAD by size:\n");
|
||||
|
||||
/* READ/WRITE statistics, per block size */
|
||||
|
||||
for ( ndx = 0; ndx < 10; ndx++) {
|
||||
if (metrics.read_by_size_count[ndx] != 0) {
|
||||
char* block_size;
|
||||
|
||||
switch ( ndx ) {
|
||||
case SIZE_512:
|
||||
block_size = "512";
|
||||
break;
|
||||
case SIZE_1K:
|
||||
block_size = "1K";
|
||||
break;
|
||||
case SIZE_2K:
|
||||
block_size = "2K";
|
||||
break;
|
||||
case SIZE_4K:
|
||||
block_size = "4K";
|
||||
break;
|
||||
case SIZE_8K:
|
||||
block_size = "8K";
|
||||
break;
|
||||
case SIZE_16K:
|
||||
block_size = "16K";
|
||||
break;
|
||||
case SIZE_32K:
|
||||
block_size = "32K";
|
||||
break;
|
||||
case SIZE_64K:
|
||||
block_size = "64K";
|
||||
break;
|
||||
case SIZE_BIGGER:
|
||||
block_size = "BIGGER";
|
||||
break;
|
||||
case SIZE_OTHER:
|
||||
block_size = "OTHER";
|
||||
break;
|
||||
default:
|
||||
block_size = "Gcc, shut up!";
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%s:%u:%u:%u\n", block_size,
|
||||
metrics.read_by_size_count[ndx],
|
||||
metrics.read_by_size_min_time[ndx],
|
||||
metrics.read_by_size_max_time[ndx]);
|
||||
}
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "\nWRITE by size:\n");
|
||||
|
||||
for ( ndx = 0; ndx < 10; ndx++) {
|
||||
if (metrics.write_by_size_count[ndx] != 0) {
|
||||
char* block_size;
|
||||
|
||||
switch ( ndx ) {
|
||||
case SIZE_512:
|
||||
block_size = "512";
|
||||
break;
|
||||
case SIZE_1K:
|
||||
block_size = "1K";
|
||||
break;
|
||||
case SIZE_2K:
|
||||
block_size = "2K";
|
||||
break;
|
||||
case SIZE_4K:
|
||||
block_size = "4K";
|
||||
break;
|
||||
case SIZE_8K:
|
||||
block_size = "8K";
|
||||
break;
|
||||
case SIZE_16K:
|
||||
block_size = "16K";
|
||||
break;
|
||||
case SIZE_32K:
|
||||
block_size = "32K";
|
||||
break;
|
||||
case SIZE_64K:
|
||||
block_size = "64K";
|
||||
break;
|
||||
case SIZE_BIGGER:
|
||||
block_size = "BIGGER";
|
||||
break;
|
||||
case SIZE_OTHER:
|
||||
block_size = "OTHER";
|
||||
break;
|
||||
default:
|
||||
block_size = "Gcc, shut up!";
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%s:%u:%u:%u\n", block_size,
|
||||
metrics.write_by_size_count[ndx],
|
||||
metrics.write_by_size_min_time[ndx],
|
||||
metrics.write_by_size_max_time[ndx]);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "\nQueues:%u:%u:%u:%u:%u:%u:%u:%u:%u\n",
|
||||
metrics.max_waiting_count,
|
||||
metrics.min_waiting_time,
|
||||
metrics.max_waiting_time,
|
||||
metrics.max_submit_count,
|
||||
metrics.min_submit_time,
|
||||
metrics.max_submit_time,
|
||||
metrics.max_complete_count,
|
||||
metrics.min_complete_time,
|
||||
metrics.max_complete_time);
|
||||
|
||||
(void)fprintf(stdout, "Hardware Ports:%u:%u:%u:%u\n",
|
||||
metrics.command_collisions,
|
||||
metrics.command_too_busy,
|
||||
metrics.max_eata_tries,
|
||||
metrics.min_eata_tries);
|
||||
|
||||
return(0);
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
# @(#)Makefile 8.1 (Berkeley) 5/31/93
|
||||
# $Id: Makefile,v 1.1 1998/01/23 02:45:53 ShimonR Exp ShimonR $
|
||||
|
||||
PROG= dpt_led
|
||||
SRCS= dpt_led.c
|
||||
|
||||
CFLAGS+=-Wall -I../../../sys -I/usr/src/sys
|
||||
BINMODE=500
|
||||
BINOWN= root
|
||||
MAN8= dpt_led.8
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,3 +0,0 @@
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
@@ -1,121 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 by Simon Shapiro
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
/* dpt_led.c: Show the blinking LED array status of a DPT HBAs */
|
||||
|
||||
#ident "$Id: dpt_led.c,v 1.1 1998/01/23 02:45:53 ShimonR Exp ShimonR $"
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
#include <sys/dpt.h>
|
||||
|
||||
int
|
||||
main(int argc, char **argv, char **argp)
|
||||
{
|
||||
eata_pt_t pass_thru;
|
||||
int led;
|
||||
|
||||
int result;
|
||||
int fd;
|
||||
|
||||
if ( (fd = open(argv[1], O_RDWR, S_IRUSR | S_IWUSR)) == -1 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to open \"%s\" - %s\n",
|
||||
argv[0], argv[1], strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
pass_thru.eataID[0] = 'E';
|
||||
pass_thru.eataID[1] = 'A';
|
||||
pass_thru.eataID[2] = 'T';
|
||||
pass_thru.eataID[3] = 'A';
|
||||
pass_thru.command = DPT_BLINKLED;
|
||||
pass_thru.command_buffer = (u_int8_t *)&led;
|
||||
|
||||
if ( (result = ioctl(fd, DPT_IOCTL_SEND, &pass_thru)) != 0 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to send IOCTL %x - %s\n",
|
||||
argv[0], DPT_IOCTL_SEND,
|
||||
strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%s\n", i2bin((unsigned int)led, 16));
|
||||
return(0);
|
||||
}
|
||||
|
||||
/*
|
||||
* and this one presents an integer as ones and zeros
|
||||
*/
|
||||
static char i2bin_bitmap[48]; /* Used for binary dump of registers */
|
||||
|
||||
char *
|
||||
i2bin(unsigned int no, int length)
|
||||
{
|
||||
int ndx, rind;
|
||||
|
||||
for (ndx = 0, rind = 0; ndx < 32; ndx++, rind++) {
|
||||
i2bin_bitmap[rind] = (((no << ndx) & 0x80000000) ? '1' : '0');
|
||||
|
||||
if (((ndx % 4) == 3))
|
||||
i2bin_bitmap[++rind] = ' ';
|
||||
}
|
||||
|
||||
if ((ndx % 4) == 3)
|
||||
i2bin_bitmap[rind - 1] = '\0';
|
||||
else
|
||||
i2bin_bitmap[rind] = '\0';
|
||||
|
||||
switch (length) {
|
||||
case 8:
|
||||
return (i2bin_bitmap + 30);
|
||||
break;
|
||||
case 16:
|
||||
return (i2bin_bitmap + 20);
|
||||
break;
|
||||
case 24:
|
||||
return (i2bin_bitmap + 10);
|
||||
break;
|
||||
case 32:
|
||||
return (i2bin_bitmap);
|
||||
default:
|
||||
return ("i2bin: Invalid length Specs");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,12 +0,0 @@
|
||||
# @(#)Makefile 8.1 (Berkeley) 5/31/93
|
||||
# $Id: Makefile,v 1.4 1998/01/21 17:41:39 ShimonR Exp $
|
||||
|
||||
PROG= dpt_sig
|
||||
SRCS= dpt_sig.c
|
||||
|
||||
CFLAGS+=-Wall -I../../../sys -I/usr/src/sys
|
||||
BINMODE=500
|
||||
BINOWN= root
|
||||
MAN8= dpt_sig.8
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,3 +0,0 @@
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
@@ -1,596 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 by Simon Shapiro
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
/* dpt_sig.c: Dunp a DPT Signature */
|
||||
|
||||
#ident "$Id: dpt_sig.c,v 1.6 1998/01/22 22:06:30 ShimonR Exp ShimonR $"
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
#define DPT_MEASURE_PERFORMANCE
|
||||
|
||||
#include <sys/dpt.h>
|
||||
|
||||
/* A primitive subset of isgraph. Used by hex_dump below */
|
||||
#define IsGraph(val) ( (((val) >= ' ') && ((val) <= '~')) )
|
||||
|
||||
/*
|
||||
* This function dumps bytes to the screen in hex format.
|
||||
*/
|
||||
void
|
||||
hex_dump(u_int8_t * data, int length, char *name, int no)
|
||||
{
|
||||
int line, column, ndx;
|
||||
|
||||
(void)fprintf(stdout, "Kernel Hex Dump for %s-%d at %p (%d bytes)\n",
|
||||
name, no, data, length);
|
||||
|
||||
/* Zero out all the counters and repeat for as many bytes as we have */
|
||||
for (ndx = 0, column = 0, line = 0; ndx < length; ndx++) {
|
||||
/* Print relative offset at the beginning of every line */
|
||||
if (column == 0)
|
||||
(void)fprintf(stdout, "%04x ", ndx);
|
||||
|
||||
/* Print the byte as two hex digits, followed by a space */
|
||||
(void)fprintf(stdout, "%02x ", data[ndx]);
|
||||
|
||||
/* Split the row of 16 bytes in half */
|
||||
if (++column == 8) {
|
||||
(void)fprintf(stdout, " ");
|
||||
}
|
||||
/* St the end of each row of 16 bytes, put a space ... */
|
||||
if (column == 16) {
|
||||
(void)fprintf(stdout, " ");
|
||||
|
||||
/* ... and then print the ASCII-visible on a line. */
|
||||
for (column = 0; column < 16; column++) {
|
||||
int ascii_pos = ndx - 15 + column;
|
||||
|
||||
/*
|
||||
* Non-printable and non-ASCII are just a
|
||||
* dot. ;-(
|
||||
*/
|
||||
if (IsGraph(data[ascii_pos]))
|
||||
(void)fprintf(stdout, "%c", data[ascii_pos]);
|
||||
else
|
||||
(void)fprintf(stdout, ".");
|
||||
}
|
||||
|
||||
/* Each line ends with a new line */
|
||||
(void)fprintf(stdout, "\n");
|
||||
column = 0;
|
||||
|
||||
/*
|
||||
* Every 256 bytes (16 lines of 16 bytes each) have
|
||||
* an empty line, separating them from the next
|
||||
* ``page''. Yes, I programmed on a Z-80, where a
|
||||
* page was 256 bytes :-)
|
||||
*/
|
||||
if (++line > 15) {
|
||||
(void)fprintf(stdout, "\n");
|
||||
line = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* We are basically done. We do want, however, to handle the ASCII
|
||||
* translation of fractional lines.
|
||||
*/
|
||||
if ((ndx == length) && (column != 0)) {
|
||||
int modulus = 16 - column, spaces = modulus * 3, skip;
|
||||
|
||||
/*
|
||||
* Skip to the right, as many spaces as there are bytes
|
||||
* ``missing'' ...
|
||||
*/
|
||||
for (skip = 0; skip < spaces; skip++)
|
||||
(void)fprintf(stdout, " ");
|
||||
|
||||
/* ... And the gap separating the hex dump from the ASCII */
|
||||
(void)fprintf(stdout, " ");
|
||||
|
||||
/*
|
||||
* Do not forget the extra space that splits the hex dump
|
||||
* vertically
|
||||
*/
|
||||
if (column < 8)
|
||||
(void)fprintf(stdout, " ");
|
||||
|
||||
for (column = 0; column < (16 - modulus); column++) {
|
||||
int ascii_pos = ndx - (16 - modulus) + column;
|
||||
|
||||
if (IsGraph(data[ascii_pos]))
|
||||
(void)fprintf(stdout, "%c", data[ascii_pos]);
|
||||
else
|
||||
(void)fprintf(stdout, ".");
|
||||
}
|
||||
(void)fprintf(stdout, "\n");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
main(int argc, char **argv, char **argp)
|
||||
{
|
||||
eata_pt_t pass_thru;
|
||||
dpt_sig_t signature;
|
||||
char *sp1;
|
||||
char *sp2;
|
||||
|
||||
int result;
|
||||
int fd;
|
||||
int ndx;
|
||||
|
||||
/* If we do not do that, gcc complains about uninitialized usage (?) */
|
||||
sp1 = "Unknown";
|
||||
sp2 = "Unknown";
|
||||
|
||||
if ( (fd = open(argv[1], O_RDWR, S_IRUSR | S_IWUSR)) == -1 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to open \"%s\" - %s\n",
|
||||
argv[0], argv[1], strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
pass_thru.eataID[0] = 'E';
|
||||
pass_thru.eataID[1] = 'A';
|
||||
pass_thru.eataID[2] = 'T';
|
||||
pass_thru.eataID[3] = 'A';
|
||||
pass_thru.command = DPT_SIGNATURE;
|
||||
pass_thru.command_buffer = (u_int8_t *)&signature;
|
||||
|
||||
if ( (result = ioctl(fd, DPT_IOCTL_SEND, &pass_thru)) != 0 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to send IOCTL %x - %s\n",
|
||||
argv[0], DPT_IOCTL_SEND,
|
||||
strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
/* dsSignature is not null terminated! */
|
||||
for (ndx = 0; ndx < sizeof(signature.dsSignature); ndx++)
|
||||
(void)fputc(signature.dsSignature[ndx], stdout);
|
||||
|
||||
(void)fprintf(stdout, ":%x:", signature.SigVersion);
|
||||
|
||||
switch (signature.ProcessorFamily) {
|
||||
case PROC_INTEL:
|
||||
sp1 = "Intel";
|
||||
switch ( signature.Processor ) {
|
||||
case PROC_8086:
|
||||
sp2 = "8086";
|
||||
break;
|
||||
case PROC_286:
|
||||
sp2 = "80286";
|
||||
break;
|
||||
case PROC_386:
|
||||
sp2 = "386";
|
||||
break;
|
||||
case PROC_486:
|
||||
sp2 = "486";
|
||||
break;
|
||||
case PROC_PENTIUM:
|
||||
sp2 = "Pentium";
|
||||
break;
|
||||
case PROC_P6:
|
||||
sp2 = "PentiumPro";
|
||||
break;
|
||||
default:
|
||||
sp2 = "Unknown Processor";
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case PROC_MOTOROLA:
|
||||
sp1 = "Motorola";
|
||||
switch ( signature.Processor ) {
|
||||
case PROC_68000:
|
||||
sp2 = "68000";
|
||||
break;
|
||||
case PROC_68020:
|
||||
sp2 = "68020";
|
||||
break;
|
||||
case PROC_68030:
|
||||
sp2 = "68030";
|
||||
break;
|
||||
case PROC_68040:
|
||||
sp2 = "68040";
|
||||
break;
|
||||
default:
|
||||
sp2 = "Unknown Processor";
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case PROC_MIPS4000:
|
||||
sp1 = "MIPS/SGI";
|
||||
break;
|
||||
case PROC_ALPHA:
|
||||
sp1 = "DEC Alpha";
|
||||
break;
|
||||
default:
|
||||
sp1 = "Unknown Processor Family";
|
||||
break;
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%s:%s:", sp1, sp2);
|
||||
|
||||
switch ( signature.Filetype ) {
|
||||
case FT_EXECUTABLE:
|
||||
sp1 = "Executable";
|
||||
break;
|
||||
case FT_SCRIPT:
|
||||
sp1 = "Script";
|
||||
break;
|
||||
case FT_HBADRVR:
|
||||
sp1 = "HBA Driver";
|
||||
break;
|
||||
case FT_OTHERDRVR:
|
||||
sp1 = "Other Driver";
|
||||
break;
|
||||
case FT_IFS:
|
||||
sp1 = "Installable FileSystem";
|
||||
break;
|
||||
case FT_ENGINE:
|
||||
sp1 = "DPT Engine";
|
||||
break;
|
||||
case FT_COMPDRVR:
|
||||
sp1 = "Compressed Driver";
|
||||
break;
|
||||
case FT_LANGUAGE:
|
||||
sp1 = "Language File";
|
||||
break;
|
||||
case FT_FIRMWARE:
|
||||
sp1 = "DownLoadable Firmware";
|
||||
break;
|
||||
case FT_COMMMODL:
|
||||
sp1 = "Communications Module";
|
||||
break;
|
||||
case FT_INT13:
|
||||
sp1 = "INT13 Type HBA Driver";
|
||||
break;
|
||||
case FT_HELPFILE:
|
||||
sp1 = "Help File";
|
||||
break;
|
||||
case FT_LOGGER:
|
||||
sp1 = "Event Logger";
|
||||
break;
|
||||
case FT_INSTALL:
|
||||
sp1 = "Installation Procedure";
|
||||
break;
|
||||
case FT_LIBRARY:
|
||||
sp1 = "Storage Manager Real-Mode Call";
|
||||
break;
|
||||
case FT_RESOURCE:
|
||||
sp1 = "Storage Manager Resource File";
|
||||
break;
|
||||
case FT_MODEM_DB:
|
||||
sp1 = "Storage Manager Modem Database";
|
||||
break;
|
||||
default:
|
||||
sp1 = "Unknown File Type";
|
||||
break;
|
||||
}
|
||||
|
||||
switch ( signature.FiletypeFlags ) {
|
||||
case FTF_DLL:
|
||||
sp2 = "Dynamically Linked Library";
|
||||
break;
|
||||
case FTF_NLM:
|
||||
sp2 = "NetWare Loadable Module";
|
||||
break;
|
||||
case FTF_OVERLAYS:
|
||||
sp2 = "Uses Overlays";
|
||||
break;
|
||||
case FTF_DEBUG:
|
||||
sp2 = "Debug Version";
|
||||
break;
|
||||
case FTF_TSR:
|
||||
sp2 = "DOS Terminate-n-Stay Resident Thing";
|
||||
break;
|
||||
case FTF_SYS:
|
||||
sp2 = "DOS Loadable Driver";
|
||||
break;
|
||||
case FTF_PROTECTED:
|
||||
sp2 = "Runs in Protected Mode";
|
||||
break;
|
||||
case FTF_APP_SPEC:
|
||||
sp2 = "Application Specific";
|
||||
break;
|
||||
default:
|
||||
sp2 = "Unknown File Type Flag";
|
||||
break;
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%s:%s:", sp1, sp2);
|
||||
|
||||
switch ( signature.OEM ) {
|
||||
case OEM_DPT:
|
||||
sp1 = "DPT";
|
||||
break;
|
||||
case OEM_ATT:
|
||||
sp1 = "AT&T";
|
||||
break;
|
||||
case OEM_NEC:
|
||||
sp1 = "NEC";
|
||||
break;
|
||||
case OEM_ALPHA:
|
||||
sp1 = "Alphatronix";
|
||||
break;
|
||||
case OEM_AST:
|
||||
sp1 = "AST";
|
||||
break;
|
||||
case OEM_OLIVETTI:
|
||||
sp1 = "Olivetti";
|
||||
break;
|
||||
case OEM_SNI:
|
||||
sp1 = "Siemens/Nixdorf";
|
||||
break;
|
||||
default:
|
||||
sp1 = "Unknown OEM";
|
||||
break;
|
||||
}
|
||||
|
||||
switch ( signature.OS ) {
|
||||
case OS_DOS:
|
||||
sp2 = "DOS";
|
||||
break;
|
||||
case OS_WINDOWS:
|
||||
sp2 = "Microsoft Windows 3.x";
|
||||
break;
|
||||
case OS_WINDOWS_NT:
|
||||
sp2 = "Microsoft Windows NT";
|
||||
break;
|
||||
case OS_OS2M:
|
||||
sp2 = "OS/2 1.2.x,MS 1.3.0,IBM 1.3.x";
|
||||
break;
|
||||
case OS_OS2L:
|
||||
sp2 = "Microsoft OS/2 1.301 - LADDR";
|
||||
break;
|
||||
case OS_OS22x:
|
||||
sp2 = "IBM OS/2 2.x";
|
||||
break;
|
||||
case OS_NW286:
|
||||
sp2 = "Novell NetWare 286";
|
||||
break;
|
||||
case OS_NW386:
|
||||
sp2 = "Novell NetWare 386";
|
||||
break;
|
||||
case OS_GEN_UNIX:
|
||||
sp2 = "Generic Unix";
|
||||
break;
|
||||
case OS_SCO_UNIX:
|
||||
sp2 = "SCO Unix";
|
||||
break;
|
||||
case OS_ATT_UNIX:
|
||||
sp2 = "AT&T Unix";
|
||||
break;
|
||||
case OS_UNIXWARE:
|
||||
sp2 = "UnixWare Unix";
|
||||
break;
|
||||
case OS_INT_UNIX:
|
||||
sp2 = "Interactive Unix";
|
||||
break;
|
||||
case OS_SOLARIS:
|
||||
sp2 = "SunSoft Solaris";
|
||||
break;
|
||||
case OS_QNX:
|
||||
sp2 = "QNX for Tom Moch";
|
||||
break;
|
||||
case OS_NEXTSTEP:
|
||||
sp2 = "NeXTSTEP";
|
||||
break;
|
||||
case OS_BANYAN:
|
||||
sp2 = "Banyan Vines";
|
||||
break;
|
||||
case OS_OLIVETTI_UNIX:
|
||||
sp2 = "Olivetti Unix";
|
||||
break;
|
||||
case OS_FREEBSD:
|
||||
sp2 = "FreeBSD 2.2 and later";
|
||||
break;
|
||||
case OS_OTHER:
|
||||
sp2 = "Other";
|
||||
break;
|
||||
default:
|
||||
sp2 = "Unknown O/S";
|
||||
break;
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%s:%s:\n", sp1, sp2);
|
||||
|
||||
if ( signature.Capabilities & CAP_RAID0 )
|
||||
(void)fprintf(stdout, "RAID-0:");
|
||||
|
||||
if ( signature.Capabilities & CAP_RAID1 )
|
||||
(void)fprintf(stdout, "RAID-1:");
|
||||
|
||||
if ( signature.Capabilities & CAP_RAID3 )
|
||||
(void)fprintf(stdout, "RAID-3:");
|
||||
|
||||
if ( signature.Capabilities & CAP_RAID5 )
|
||||
(void)fprintf(stdout, "RAID-5:");
|
||||
|
||||
if ( signature.Capabilities & CAP_SPAN )
|
||||
(void)fprintf(stdout, "SPAN:");
|
||||
|
||||
if ( signature.Capabilities & CAP_PASS )
|
||||
(void)fprintf(stdout, "PASS:");
|
||||
|
||||
if ( signature.Capabilities & CAP_OVERLAP )
|
||||
(void)fprintf(stdout, "OVERLAP:");
|
||||
|
||||
if ( signature.Capabilities & CAP_ASPI )
|
||||
(void)fprintf(stdout, "ASPI:");
|
||||
|
||||
if ( signature.Capabilities & CAP_ABOVE16MB )
|
||||
(void)fprintf(stdout, "ISA16MB:");
|
||||
|
||||
if ( signature.Capabilities & CAP_EXTEND )
|
||||
(void)fprintf(stdout, "ISA16MB:");
|
||||
|
||||
(void)fprintf(stdout, "\n");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_DASD )
|
||||
(void)fprintf(stdout, "DASD:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_TAPE )
|
||||
(void)fprintf(stdout, "Tape:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_PRINTER )
|
||||
(void)fprintf(stdout, "Printer:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_PROC )
|
||||
(void)fprintf(stdout, "CPU:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_WORM )
|
||||
(void)fprintf(stdout, "WORM:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_CDROM )
|
||||
(void)fprintf(stdout, "CDROM:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_SCANNER )
|
||||
(void)fprintf(stdout, "Scanner:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_OPTICAL )
|
||||
(void)fprintf(stdout, "Optical:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_JUKEBOX )
|
||||
(void)fprintf(stdout, "Jukebox:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_COMM )
|
||||
(void)fprintf(stdout, "Comm:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_OTHER )
|
||||
(void)fprintf(stdout, "Other:");
|
||||
|
||||
if ( signature.DeviceSupp & DEV_ALL )
|
||||
(void)fprintf(stdout, "All:");
|
||||
|
||||
(void)fprintf(stdout, "\n");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_2001 )
|
||||
(void)fprintf(stdout, "PM2001:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_2012A )
|
||||
(void)fprintf(stdout, "PM2012A:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_PLUS_ISA )
|
||||
(void)fprintf(stdout, "PM2011+PM2021:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_PLUS_EISA )
|
||||
(void)fprintf(stdout, "PM2012B+PM2022:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_SC3_ISA )
|
||||
(void)fprintf(stdout, "PM2021:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_SC3_EISA )
|
||||
(void)fprintf(stdout, "PM2022+PM2122:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_SC3_PCI )
|
||||
(void)fprintf(stdout, "SmartCache III PCI:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_SC4_ISA )
|
||||
(void)fprintf(stdout, "SmartCache IV ISA:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_SC4_EISA )
|
||||
(void)fprintf(stdout, "SmartCache IV EISA:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_SC4_PCI )
|
||||
(void)fprintf(stdout, "SmartCache IV PCI:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_ALL_MASTER )
|
||||
(void)fprintf(stdout, "All Bus Mastering:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_ALL_CACHE )
|
||||
(void)fprintf(stdout, "All Caching:");
|
||||
|
||||
if ( signature.AdapterSupp & ADF_ALL )
|
||||
(void)fprintf(stdout, "All HBAs:");
|
||||
|
||||
(void)fprintf(stdout, "\n");
|
||||
|
||||
if ( signature.Application & APP_DPTMGR )
|
||||
(void)fprintf(stdout, "DPTMGR:");
|
||||
|
||||
if ( signature.Application & APP_ENGINE )
|
||||
(void)fprintf(stdout, "Engine:");
|
||||
|
||||
if ( signature.Application & APP_SYTOS )
|
||||
(void)fprintf(stdout, "Systron Sytos Plus:");
|
||||
|
||||
if ( signature.Application & APP_CHEYENNE )
|
||||
(void)fprintf(stdout, "Cheyenne ARCServe + ARCSolo:");
|
||||
|
||||
if ( signature.Application & APP_MSCDEX )
|
||||
(void)fprintf(stdout, "Microsoft CD-ROM extensions:");
|
||||
|
||||
if ( signature.Application & APP_NOVABACK )
|
||||
(void)fprintf(stdout, "NovaStor Novaback:");
|
||||
|
||||
if ( signature.Application & APP_AIM )
|
||||
(void)fprintf(stdout, "Archive Information Manager:");
|
||||
|
||||
(void)fprintf(stdout, "\n");
|
||||
|
||||
if ( signature.Requirements & REQ_SMARTROM )
|
||||
(void)fprintf(stdout, "SmartROM:");
|
||||
|
||||
if ( signature.Requirements & REQ_DPTDDL )
|
||||
(void)fprintf(stdout, "DPTDDL.SYS:");
|
||||
|
||||
if ( signature.Requirements & REQ_HBA_DRIVER )
|
||||
(void)fprintf(stdout, "HBA Driver:");
|
||||
|
||||
if ( signature.Requirements & REQ_ASPI_TRAN )
|
||||
(void)fprintf(stdout, "ASPI Transport Modules:");
|
||||
|
||||
if ( signature.Requirements & REQ_ENGINE )
|
||||
(void)fprintf(stdout, "DPT Engine:");
|
||||
|
||||
if ( signature.Requirements & REQ_COMM_ENG )
|
||||
(void)fprintf(stdout, "DPT Comm Engine:");
|
||||
|
||||
(void)fprintf(stdout, "\n");
|
||||
|
||||
(void)fprintf(stdout, "%x.%x.%x:%d.%d.%d\n",
|
||||
signature.Version, signature.Revision,
|
||||
signature.SubRevision,
|
||||
signature.Month, signature.Day, signature.Year + 1980);
|
||||
|
||||
return(0);
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
# @(#)Makefile 8.1 (Berkeley) 5/31/93
|
||||
# $Id: Makefile,v 1.3 1998/01/21 07:50:38 ShimonR Exp ShimonR $
|
||||
|
||||
PROG= dpt_softc
|
||||
SRCS= dpt_softc.c
|
||||
|
||||
CFLAGS+=-Wall -I../../../sys -I/usr/src/sys
|
||||
BINMODE=500
|
||||
BINOWN= root
|
||||
MAN8= dpt_softc.8
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,4 +0,0 @@
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
|
||||
@@ -1,188 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 by Simon Shapiro
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
/* dpt_softc.c: Dunp a DPT control structure */
|
||||
|
||||
#ident "$Id: dpt_softc.c,v 1.7 1998/01/22 21:37:40 ShimonR Exp $"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
/*
|
||||
* The following two defines alter the size and composition of dpt_softc_t.
|
||||
* If useland does not match the kenel, disaster will ensue.
|
||||
* Since we do not know how to pick up kernel options from here,
|
||||
* and since we always use these options, we will enable them here.
|
||||
*
|
||||
* If you build a kernel without these options, edit here and recompile.
|
||||
*/
|
||||
#define DPT_MEASURE_PERFORMANCE
|
||||
#define DEVFS
|
||||
|
||||
#include <sys/dpt.h>
|
||||
|
||||
static char i2bin_bitmap[48]; /* Used for binary dump of registers */
|
||||
|
||||
char *
|
||||
i2bin(unsigned int no, int length)
|
||||
{
|
||||
int ndx, rind;
|
||||
|
||||
for (ndx = 0, rind = 0; ndx < 32; ndx++, rind++) {
|
||||
i2bin_bitmap[rind] = (((no << ndx) & 0x80000000) ? '1' : '0');
|
||||
|
||||
if (((ndx % 4) == 3))
|
||||
i2bin_bitmap[++rind] = ' ';
|
||||
}
|
||||
|
||||
if ((ndx % 4) == 3)
|
||||
i2bin_bitmap[rind - 1] = '\0';
|
||||
else
|
||||
i2bin_bitmap[rind] = '\0';
|
||||
|
||||
switch (length) {
|
||||
case 8:
|
||||
return (i2bin_bitmap + 30);
|
||||
break;
|
||||
case 16:
|
||||
return (i2bin_bitmap + 20);
|
||||
break;
|
||||
case 24:
|
||||
return (i2bin_bitmap + 10);
|
||||
break;
|
||||
case 32:
|
||||
return (i2bin_bitmap);
|
||||
default:
|
||||
return ("i2bin: Invalid length Specs");
|
||||
break;
|
||||
}
|
||||
}
|
||||
int
|
||||
main(int argc, char **argv, char **argp)
|
||||
{
|
||||
dpt_user_softc_t udpt;
|
||||
int result;
|
||||
int fd;
|
||||
|
||||
if ( (fd = open(argv[1], O_RDWR, S_IRUSR | S_IWUSR)) == -1 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to open \"%s\" - %s\n",
|
||||
argv[0], argv[1], strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if ( (result = ioctl(fd, DPT_IOCTL_SOFTC, &udpt)) != 0 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to send IOCTL %x - %s\n",
|
||||
argv[0], DPT_IOCTL_SOFTC,
|
||||
strerror(errno));
|
||||
exit(2);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "Counters:%d:%d:%d:%d:%d:%d:%d\n",
|
||||
udpt.total_ccbs_count,
|
||||
udpt.free_ccbs_count,
|
||||
udpt.waiting_ccbs_count,
|
||||
udpt.submitted_ccbs_count,
|
||||
udpt.completed_ccbs_count,
|
||||
udpt.commands_processed,
|
||||
udpt.lost_interrupts);
|
||||
|
||||
(void)fprintf(stdout, "Queue Status:%s\n",
|
||||
i2bin(udpt.queue_status, sizeof(udpt.queue_status) * 8));
|
||||
|
||||
(void)fprintf(stdout, "Free lock:%s\n",
|
||||
i2bin(udpt.free_lock, sizeof(udpt.free_lock) * 8));
|
||||
|
||||
(void)fprintf(stdout, "Waiting lock:%s\n",
|
||||
i2bin(udpt.waiting_lock, sizeof(udpt.waiting_lock) * 8));
|
||||
|
||||
(void)fprintf(stdout, "Submitted lock:%s\n",
|
||||
i2bin(udpt.submitted_lock, sizeof(udpt.submitted_lock) * 8));
|
||||
|
||||
(void)fprintf(stdout, "Completed lock:%s\n",
|
||||
i2bin(udpt.completed_lock, sizeof(udpt.completed_lock) * 8));
|
||||
|
||||
(void)fprintf(stdout, "Configuration:%s:%d:%d:%d:%x:%d:%d\n",
|
||||
udpt.handle_interrupts ? "Yes" : "No",
|
||||
udpt.max_id,
|
||||
udpt.max_lun,
|
||||
udpt.channels,
|
||||
udpt.io_base,
|
||||
udpt.irq,
|
||||
udpt.dma_channel);
|
||||
|
||||
(void)fprintf(stdout, "ID:%x:%x:%s:%s:%s:%s:%x\n",
|
||||
udpt.board_data.deviceType,
|
||||
udpt.board_data.rm_dtq,
|
||||
udpt.board_data.vendor,
|
||||
udpt.board_data.modelNum,
|
||||
udpt.board_data.firmware,
|
||||
udpt.board_data.protocol,
|
||||
udpt.EATA_revision);
|
||||
|
||||
(void)fprintf(stdout,"Capabilities:%x:%d:%s:%s:%s:%s:%s\n",
|
||||
udpt.bustype,
|
||||
udpt.channels,
|
||||
i2bin((u_int32_t)udpt.state, sizeof(udpt.state) * 8),
|
||||
udpt.primary ? "Yes" : "No",
|
||||
udpt.more_support ? "Yes" : "No",
|
||||
udpt.immediate_support ? "Yes" : "No",
|
||||
udpt.broken_INQUIRY ? "Yes" : "No");
|
||||
|
||||
(void)fprintf(stdout,"More Config:%d:%d:%d:%d:%d:%d:%d:%d:%d:%d\n",
|
||||
udpt.resetlevel[0],
|
||||
udpt.resetlevel[1],
|
||||
udpt.resetlevel[2],
|
||||
udpt.cplen,
|
||||
udpt.cppadlen,
|
||||
udpt.queuesize,
|
||||
udpt.sgsize,
|
||||
udpt.hostid[0],
|
||||
udpt.hostid[1],
|
||||
udpt.hostid[2]);
|
||||
|
||||
(void)fprintf(stdout,"Cache:%s:%d\n",
|
||||
(udpt.cache_type == DPT_NO_CACHE)
|
||||
? "None"
|
||||
: (udpt.cache_type == DPT_CACHE_WRITETHROUGH)
|
||||
? "Write-Through" : "Write-Back",
|
||||
udpt.cache_size);
|
||||
|
||||
return(0);
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
# @(#)Makefile 8.1 (Berkeley) 5/31/93
|
||||
# $Id: Makefile,v 1.1 1998/01/22 23:32:27 ShimonR Exp ShimonR $
|
||||
|
||||
PROG= dpt_sysinfo
|
||||
SRCS= dpt_sysinfo.c
|
||||
|
||||
CFLAGS+=-Wall -I../../../sys -I/usr/src/sys
|
||||
BINMODE=500
|
||||
BINOWN= root
|
||||
MAN8= dpt_sysinfo.8
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
@@ -1,3 +0,0 @@
|
||||
.\" Copyright (c) 1997 Simon Shapiro. All rights reserved.
|
||||
.\"
|
||||
.\" There is nothing here yet, but an empty file will not patch
|
||||
@@ -1,256 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1997 by Simon Shapiro
|
||||
* All Rights Reserved
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions, and the following disclaimer,
|
||||
* without modification, immediately at the beginning of the file.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
/* dpt_ctlinfo.c: Dunp a DPT HBA Information Block */
|
||||
|
||||
#ident "$Id: dpt_ctlinfo.c,v 1.1 1998/01/22 23:32:27 ShimonR Exp ShimonR $"
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/queue.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <scsi/scsi_all.h>
|
||||
#include <scsi/scsi_message.h>
|
||||
#include <scsi/scsiconf.h>
|
||||
|
||||
#define DPT_MEASURE_PERFORMANCE
|
||||
|
||||
#include <sys/dpt.h>
|
||||
|
||||
|
||||
int
|
||||
main(int argc, char **argv, char **argp)
|
||||
{
|
||||
eata_pt_t pass_thru;
|
||||
dpt_sysinfo_t sysinfo;
|
||||
|
||||
int result;
|
||||
int fd;
|
||||
int ndx;
|
||||
|
||||
if ( (fd = open(argv[1], O_RDWR, S_IRUSR | S_IWUSR)) == -1 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to open \"%s\" - %s\n",
|
||||
argv[0], argv[1], strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
pass_thru.eataID[0] = 'E';
|
||||
pass_thru.eataID[1] = 'A';
|
||||
pass_thru.eataID[2] = 'T';
|
||||
pass_thru.eataID[3] = 'A';
|
||||
pass_thru.command = DPT_SYSINFO;
|
||||
pass_thru.command_buffer = (u_int8_t *)&sysinfo;
|
||||
|
||||
if ( (result = ioctl(fd, DPT_IOCTL_SEND, &pass_thru)) != 0 ) {
|
||||
(void)fprintf(stderr, "%s ERROR: Failed to send IOCTL %x - %s\n",
|
||||
argv[0], DPT_IOCTL_SEND,
|
||||
strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%x:%x:%d:",
|
||||
sysinfo.drive0CMOS, sysinfo.drive1CMOS, sysinfo.numDrives);
|
||||
|
||||
switch (sysinfo.processorFamily) {
|
||||
case PROC_INTEL:
|
||||
(void)fprintf(stdout, "Intel:");
|
||||
switch (sysinfo.processorType) {
|
||||
case PROC_8086:
|
||||
(void)fprintf(stdout, "8086:");
|
||||
break;
|
||||
case PROC_286:
|
||||
(void)fprintf(stdout, "80286:");
|
||||
break;
|
||||
case PROC_386:
|
||||
(void)fprintf(stdout, "i386:");
|
||||
break;
|
||||
case PROC_486:
|
||||
(void)fprintf(stdout, "80486:");
|
||||
break;
|
||||
case PROC_PENTIUM:
|
||||
(void)fprintf(stdout, "Pentium:");
|
||||
break;
|
||||
case PROC_P6:
|
||||
(void)fprintf(stdout, "Pentium-Pro:");
|
||||
break;
|
||||
default:
|
||||
(void)fprintf(stdout, "Unknown (%d):", sysinfo.processorType);
|
||||
}
|
||||
break;
|
||||
case PROC_MOTOROLA:
|
||||
(void)fprintf(stdout, "Motorola:");
|
||||
switch (sysinfo.processorType) {
|
||||
case PROC_68000:
|
||||
(void)fprintf(stdout, "M68000");
|
||||
break;
|
||||
case PROC_68020:
|
||||
(void)fprintf(stdout, "M68020");
|
||||
break;
|
||||
case PROC_68030:
|
||||
(void)fprintf(stdout, "M68030");
|
||||
break;
|
||||
case PROC_68040:
|
||||
(void)fprintf(stdout, "M68040");
|
||||
break;
|
||||
default:
|
||||
(void)fprintf(stdout, "Unknown (%d):", sysinfo.processorType);
|
||||
}
|
||||
break;
|
||||
case PROC_MIPS4000:
|
||||
(void)fprintf(stdout, "MIPS:Any:");
|
||||
break;
|
||||
case PROC_ALPHA:
|
||||
(void)fprintf(stdout, "Alpha:Any:");
|
||||
break;
|
||||
default:
|
||||
(void)fprintf(stdout, "Unknown (%d):Any:", sysinfo.processorFamily);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%d.%d.%d:",
|
||||
sysinfo.smartROMMajorVersion,
|
||||
sysinfo.smartROMMinorVersion,
|
||||
sysinfo.smartROMRevision);
|
||||
|
||||
(void)fprintf(stdout, "%c%c%c%c%c%c%c%c%c%c%c:",
|
||||
(sysinfo.flags & SI_CMOS_Valid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_NumDrivesValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_ProcessorValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_MemorySizeValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_DriveParamsValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_SmartROMverValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_OSversionValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_OSspecificValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_BusTypeValid) ? '+' : '-',
|
||||
(sysinfo.flags & SI_ALL_VALID) ? '+' : '-',
|
||||
(sysinfo.flags & SI_NO_SmartROM) ? '+' : '-');
|
||||
|
||||
(void)fprintf(stdout, "%d:", sysinfo.conventionalMemSize);
|
||||
(void)fprintf(stdout, "%d:", sysinfo.extendedMemSize);
|
||||
|
||||
switch (sysinfo.osType) {
|
||||
case OS_DOS:
|
||||
(void)fprintf(stdout, "DOS:");
|
||||
break;
|
||||
case OS_WINDOWS:
|
||||
(void)fprintf(stdout, "Win3.1:");
|
||||
break;
|
||||
case OS_WINDOWS_NT:
|
||||
(void)fprintf(stdout, "NT:");
|
||||
break;
|
||||
case OS_OS2M:
|
||||
(void)fprintf(stdout, "OS/2-std:");
|
||||
break;
|
||||
case OS_OS2L:
|
||||
(void)fprintf(stdout, "OS/2-LADDR:");
|
||||
break;
|
||||
case OS_OS22x:
|
||||
(void)fprintf(stdout, "OS/2-2.x:");
|
||||
break;
|
||||
case OS_NW286:
|
||||
(void)fprintf(stdout, "NetWare-286:");
|
||||
break;
|
||||
case OS_NW386:
|
||||
(void)fprintf(stdout, "NetWare-386:");
|
||||
break;
|
||||
case OS_GEN_UNIX:
|
||||
(void)fprintf(stdout, "Unix:");
|
||||
break;
|
||||
case OS_SCO_UNIX:
|
||||
(void)fprintf(stdout, "SCO Unix:");
|
||||
break;
|
||||
case OS_ATT_UNIX:
|
||||
(void)fprintf(stdout, "AT&T Unix:");
|
||||
break;
|
||||
case OS_UNIXWARE:
|
||||
(void)fprintf(stdout, "UnixWare:");
|
||||
break;
|
||||
case OS_INT_UNIX:
|
||||
(void)fprintf(stdout, "IAC Unix:");
|
||||
break;
|
||||
case OS_SOLARIS:
|
||||
(void)fprintf(stdout, "Solaris:");
|
||||
break;
|
||||
case OS_QNX:
|
||||
(void)fprintf(stdout, "Qnx:");
|
||||
break;
|
||||
case OS_NEXTSTEP:
|
||||
(void)fprintf(stdout, "NextStep:");
|
||||
break;
|
||||
case OS_BANYAN:
|
||||
(void)fprintf(stdout, "Banyan:");
|
||||
break;
|
||||
case OS_OLIVETTI_UNIX:
|
||||
(void)fprintf(stdout, "Olivetti Unix:");
|
||||
break;
|
||||
case OS_FREEBSD:
|
||||
(void)fprintf(stdout, "FreeBSD:");
|
||||
break;
|
||||
case OS_OTHER:
|
||||
(void)fprintf(stdout, "Other (%d):", sysinfo.osType);
|
||||
break;
|
||||
default:
|
||||
(void)fprintf(stdout, "Unknown (%d):", sysinfo.osType);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "%d.%d.%d.%d:", sysinfo.osMajorVersion,
|
||||
sysinfo.osMinorVersion, sysinfo.osRevision,
|
||||
sysinfo.osSubRevision);
|
||||
|
||||
switch (sysinfo.busType) {
|
||||
case HBA_BUS_ISA:
|
||||
(void)fprintf(stdout, "ISA:");
|
||||
break;
|
||||
case HBA_BUS_EISA:
|
||||
(void)fprintf(stdout, "EISA:");
|
||||
break;
|
||||
case HBA_BUS_PCI:
|
||||
(void)fprintf(stdout, "PCI:");
|
||||
break;
|
||||
default:
|
||||
(void)fprintf(stdout, "Unknown (%d):", sysinfo.busType);
|
||||
}
|
||||
|
||||
for (ndx = 0; ndx < 16; ndx++) {
|
||||
if (sysinfo.drives[ndx].cylinders == 0)
|
||||
continue;
|
||||
(void)fprintf(stdout, "d%dc%dh%ds%d:", ndx,
|
||||
sysinfo.drives[ndx].cylinders,
|
||||
sysinfo.drives[ndx].heads,
|
||||
sysinfo.drives[ndx].sectors);
|
||||
}
|
||||
|
||||
(void)fprintf(stdout, "\n");
|
||||
|
||||
return(0);
|
||||
}
|
||||
@@ -1,88 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1995 Andrew McRae. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <pccard/cardinfo.h>
|
||||
|
||||
int
|
||||
rdattr_main(argc, argv)
|
||||
int argc;
|
||||
char *argv[];
|
||||
{
|
||||
int i, reg, length;
|
||||
char name[64];
|
||||
u_char *buf;
|
||||
int fd;
|
||||
off_t offs;
|
||||
|
||||
if (argc != 4) {
|
||||
fprintf(stderr, "usage: %s rdattr slot offs length\n", argv[0]);
|
||||
exit(1);
|
||||
}
|
||||
sprintf(name, CARD_DEVICE, atoi(argv[1]));
|
||||
fd = open(name, O_RDONLY);
|
||||
if (fd < 0) {
|
||||
perror(name);
|
||||
exit(1);
|
||||
}
|
||||
reg = MDF_ATTR;
|
||||
if (ioctl(fd, PIOCRWFLAG, ®)) {
|
||||
perror("ioctl (PIOCRWFLAG)");
|
||||
exit(1);
|
||||
}
|
||||
if (sscanf(argv[2], "%x", ®) != 1 ||
|
||||
sscanf(argv[3], "%x", &length) != 1) {
|
||||
fprintf(stderr, "arg error\n");
|
||||
exit(1);
|
||||
}
|
||||
offs = reg;
|
||||
if ((buf = malloc(length)) == 0) {
|
||||
perror(name);
|
||||
exit(1);
|
||||
}
|
||||
lseek(fd, offs, SEEK_SET);
|
||||
if (read(fd, buf, length) != length) {
|
||||
perror(name);
|
||||
exit(1);
|
||||
}
|
||||
for (i = 0; i < length; i++) {
|
||||
if (i % 16 == 0) {
|
||||
printf("%04x: ", (int) offs + i);
|
||||
}
|
||||
printf("%02x ", buf[i]);
|
||||
if (i % 16 == 15) {
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
if (i % 16 != 0) {
|
||||
printf("\n");
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@@ -1,106 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1995 Andrew McRae. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef lint
|
||||
static const char rcsid[] =
|
||||
"$Id: pccardd.c,v 1.1 1998/02/27 08:19:25 hosokawa Exp $";
|
||||
#endif /* not lint */
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
#define EXTERN
|
||||
#include "cardd.h"
|
||||
|
||||
char *config_file = "/etc/pccard.conf";
|
||||
|
||||
/*
|
||||
* mainline code for cardd
|
||||
*/
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
struct slot *slots, *sp;
|
||||
int count, dodebug = 0;
|
||||
int doverbose = 0;
|
||||
|
||||
while ((count = getopt(argc, argv, ":dvf:")) != -1) {
|
||||
switch (count) {
|
||||
case 'd':
|
||||
setbuf(stdout, 0);
|
||||
setbuf(stderr, 0);
|
||||
dodebug = 1;
|
||||
break;
|
||||
case 'v':
|
||||
doverbose = 1;
|
||||
break;
|
||||
case 'f':
|
||||
config_file = optarg;
|
||||
break;
|
||||
case ':':
|
||||
die("no config file argument");
|
||||
break;
|
||||
case '?':
|
||||
die("illegal option");
|
||||
break;
|
||||
}
|
||||
}
|
||||
#ifdef DEBUG
|
||||
dodebug = 1;
|
||||
#endif
|
||||
io_avail = bit_alloc(IOPORTS); /* Only supports ISA ports */
|
||||
|
||||
/* Mem allocation done in MEMUNIT units. */
|
||||
mem_avail = bit_alloc(MEMBLKS);
|
||||
readfile(config_file);
|
||||
if (doverbose)
|
||||
dump_config_file();
|
||||
log_setup();
|
||||
if (!dodebug)
|
||||
if (daemon(0, 0))
|
||||
die("fork failed");
|
||||
slots = readslots();
|
||||
if (slots == 0)
|
||||
die("no PC-CARD slots");
|
||||
logmsg("pccardd started", NULL);
|
||||
for (;;) {
|
||||
fd_set mask;
|
||||
FD_ZERO(&mask);
|
||||
for (sp = slots; sp; sp = sp->next)
|
||||
FD_SET(sp->fd, &mask);
|
||||
count = select(32, 0, 0, &mask, 0);
|
||||
if (count == -1) {
|
||||
logerr("select");
|
||||
continue;
|
||||
}
|
||||
if (count)
|
||||
for (sp = slots; sp; sp = sp->next)
|
||||
if (FD_ISSET(sp->fd, &mask))
|
||||
slot_change(sp);
|
||||
}
|
||||
}
|
||||
@@ -1,430 +0,0 @@
|
||||
/*
|
||||
* cbcp - Call Back Configuration Protocol.
|
||||
*
|
||||
* Copyright (c) 1995 Pedro Roque Marques
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms are permitted
|
||||
* provided that the above copyright notice and this paragraph are
|
||||
* duplicated in all such forms and that any documentation,
|
||||
* advertising materials, and other materials related to such
|
||||
* distribution and use acknowledge that the software was developed
|
||||
* by Pedro Roque Marques. The name of the author may not be used to
|
||||
* endorse or promote products derived from this software without
|
||||
* specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*/
|
||||
|
||||
#ifndef lint
|
||||
static char rcsid[] = "$Id$";
|
||||
#endif
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/time.h>
|
||||
#include <syslog.h>
|
||||
|
||||
#include "pppd.h"
|
||||
#include "cbcp.h"
|
||||
#include "fsm.h"
|
||||
#include "lcp.h"
|
||||
#include "ipcp.h"
|
||||
|
||||
/*
|
||||
* Protocol entry points.
|
||||
*/
|
||||
static void cbcp_init __P((int unit));
|
||||
static void cbcp_open __P((int unit));
|
||||
static void cbcp_lowerup __P((int unit));
|
||||
static void cbcp_input __P((int unit, u_char *pkt, int len));
|
||||
static void cbcp_protrej __P((int unit));
|
||||
static int cbcp_printpkt __P((u_char *pkt, int len,
|
||||
void (*printer) __P((void *, char *, ...)),
|
||||
void *arg));
|
||||
|
||||
struct protent cbcp_protent = {
|
||||
PPP_CBCP,
|
||||
cbcp_init,
|
||||
cbcp_input,
|
||||
cbcp_protrej,
|
||||
cbcp_lowerup,
|
||||
NULL,
|
||||
cbcp_open,
|
||||
NULL,
|
||||
cbcp_printpkt,
|
||||
NULL,
|
||||
0,
|
||||
"CBCP",
|
||||
NULL,
|
||||
NULL,
|
||||
NULL
|
||||
};
|
||||
|
||||
cbcp_state cbcp[NUM_PPP];
|
||||
|
||||
/* internal prototypes */
|
||||
|
||||
static void cbcp_recvreq __P((cbcp_state *us, char *pckt, int len));
|
||||
static void cbcp_resp __P((cbcp_state *us));
|
||||
static void cbcp_up __P((cbcp_state *us));
|
||||
static void cbcp_recvack __P((cbcp_state *us, char *pckt, int len));
|
||||
static void cbcp_send __P((cbcp_state *us, u_char code, u_char *buf, int len));
|
||||
|
||||
/* init state */
|
||||
static void
|
||||
cbcp_init(iface)
|
||||
int iface;
|
||||
{
|
||||
cbcp_state *us;
|
||||
|
||||
us = &cbcp[iface];
|
||||
memset(us, 0, sizeof(cbcp_state));
|
||||
us->us_unit = iface;
|
||||
us->us_type |= (1 << CB_CONF_NO);
|
||||
}
|
||||
|
||||
/* lower layer is up */
|
||||
static void
|
||||
cbcp_lowerup(iface)
|
||||
int iface;
|
||||
{
|
||||
cbcp_state *us = &cbcp[iface];
|
||||
|
||||
syslog(LOG_DEBUG, "cbcp_lowerup");
|
||||
syslog(LOG_DEBUG, "want: %d", us->us_type);
|
||||
|
||||
if (us->us_type == CB_CONF_USER)
|
||||
syslog(LOG_DEBUG, "phone no: %s", us->us_number);
|
||||
}
|
||||
|
||||
static void
|
||||
cbcp_open(unit)
|
||||
int unit;
|
||||
{
|
||||
syslog(LOG_DEBUG, "cbcp_open");
|
||||
}
|
||||
|
||||
/* process an incomming packet */
|
||||
static void
|
||||
cbcp_input(unit, inpacket, pktlen)
|
||||
int unit;
|
||||
u_char *inpacket;
|
||||
int pktlen;
|
||||
{
|
||||
u_char *inp;
|
||||
u_char code, id;
|
||||
u_short len;
|
||||
|
||||
cbcp_state *us = &cbcp[unit];
|
||||
|
||||
inp = inpacket;
|
||||
|
||||
if (pktlen < CBCP_MINLEN) {
|
||||
syslog(LOG_ERR, "CBCP packet is too small");
|
||||
return;
|
||||
}
|
||||
|
||||
GETCHAR(code, inp);
|
||||
GETCHAR(id, inp);
|
||||
GETSHORT(len, inp);
|
||||
|
||||
#if 0
|
||||
if (len > pktlen) {
|
||||
syslog(LOG_ERR, "CBCP packet: invalid length");
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
||||
len -= CBCP_MINLEN;
|
||||
|
||||
switch(code) {
|
||||
case CBCP_REQ:
|
||||
us->us_id = id;
|
||||
cbcp_recvreq(us, inp, len);
|
||||
break;
|
||||
|
||||
case CBCP_RESP:
|
||||
syslog(LOG_DEBUG, "CBCP_RESP received");
|
||||
break;
|
||||
|
||||
case CBCP_ACK:
|
||||
if (id != us->us_id)
|
||||
syslog(LOG_DEBUG, "id doesn't match: expected %d recv %d",
|
||||
us->us_id, id);
|
||||
|
||||
cbcp_recvack(us, inp, len);
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* protocol was rejected by foe */
|
||||
void cbcp_protrej(int iface)
|
||||
{
|
||||
}
|
||||
|
||||
char *cbcp_codenames[] = {
|
||||
"Request", "Response", "Ack"
|
||||
};
|
||||
|
||||
char *cbcp_optionnames[] = {
|
||||
"NoCallback",
|
||||
"UserDefined",
|
||||
"AdminDefined",
|
||||
"List"
|
||||
};
|
||||
|
||||
/* pretty print a packet */
|
||||
static int
|
||||
cbcp_printpkt(p, plen, printer, arg)
|
||||
u_char *p;
|
||||
int plen;
|
||||
void (*printer) __P((void *, char *, ...));
|
||||
void *arg;
|
||||
{
|
||||
int code, opt, id, len, olen, delay;
|
||||
u_char *pstart;
|
||||
|
||||
if (plen < HEADERLEN)
|
||||
return 0;
|
||||
pstart = p;
|
||||
GETCHAR(code, p);
|
||||
GETCHAR(id, p);
|
||||
GETSHORT(len, p);
|
||||
if (len < HEADERLEN || len > plen)
|
||||
return 0;
|
||||
|
||||
if (code >= 1 && code <= sizeof(cbcp_codenames) / sizeof(char *))
|
||||
printer(arg, " %s", cbcp_codenames[code-1]);
|
||||
else
|
||||
printer(arg, " code=0x%x", code);
|
||||
|
||||
printer(arg, " id=0x%x", id);
|
||||
len -= HEADERLEN;
|
||||
|
||||
switch (code) {
|
||||
case CBCP_REQ:
|
||||
case CBCP_RESP:
|
||||
case CBCP_ACK:
|
||||
while(len >= 2) {
|
||||
GETCHAR(opt, p);
|
||||
GETCHAR(olen, p);
|
||||
|
||||
if (olen < 2 || olen > len) {
|
||||
break;
|
||||
}
|
||||
|
||||
printer(arg, " <");
|
||||
len -= olen;
|
||||
|
||||
if (opt >= 1 && opt <= sizeof(cbcp_optionnames) / sizeof(char *))
|
||||
printer(arg, " %s", cbcp_optionnames[opt-1]);
|
||||
else
|
||||
printer(arg, " option=0x%x", opt);
|
||||
|
||||
if (olen > 2) {
|
||||
GETCHAR(delay, p);
|
||||
printer(arg, " delay = %d", delay);
|
||||
}
|
||||
|
||||
if (olen > 3) {
|
||||
int addrt;
|
||||
char str[256];
|
||||
|
||||
GETCHAR(addrt, p);
|
||||
memcpy(str, p, olen - 4);
|
||||
str[olen - 4] = 0;
|
||||
printer(arg, " number = %s", str);
|
||||
}
|
||||
printer(arg, ">");
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
for (; len > 0; --len) {
|
||||
GETCHAR(code, p);
|
||||
printer(arg, " %.2x", code);
|
||||
}
|
||||
|
||||
return p - pstart;
|
||||
}
|
||||
|
||||
/* received CBCP request */
|
||||
static void
|
||||
cbcp_recvreq(us, pckt, pcktlen)
|
||||
cbcp_state *us;
|
||||
char *pckt;
|
||||
int pcktlen;
|
||||
{
|
||||
u_char type, opt_len, delay, addr_type;
|
||||
char address[256];
|
||||
int len = pcktlen;
|
||||
|
||||
address[0] = 0;
|
||||
|
||||
while (len) {
|
||||
syslog(LOG_DEBUG, "length: %d", len);
|
||||
|
||||
GETCHAR(type, pckt);
|
||||
GETCHAR(opt_len, pckt);
|
||||
|
||||
if (opt_len > 2)
|
||||
GETCHAR(delay, pckt);
|
||||
|
||||
us->us_allowed |= (1 << type);
|
||||
|
||||
switch(type) {
|
||||
case CB_CONF_NO:
|
||||
syslog(LOG_DEBUG, "no callback allowed");
|
||||
break;
|
||||
|
||||
case CB_CONF_USER:
|
||||
syslog(LOG_DEBUG, "user callback allowed");
|
||||
if (opt_len > 4) {
|
||||
GETCHAR(addr_type, pckt);
|
||||
memcpy(address, pckt, opt_len - 4);
|
||||
address[opt_len - 4] = 0;
|
||||
if (address[0])
|
||||
syslog(LOG_DEBUG, "address: %s", address);
|
||||
}
|
||||
break;
|
||||
|
||||
case CB_CONF_ADMIN:
|
||||
syslog(LOG_DEBUG, "user admin defined allowed");
|
||||
break;
|
||||
|
||||
case CB_CONF_LIST:
|
||||
break;
|
||||
}
|
||||
len -= opt_len;
|
||||
}
|
||||
|
||||
cbcp_resp(us);
|
||||
}
|
||||
|
||||
static void
|
||||
cbcp_resp(us)
|
||||
cbcp_state *us;
|
||||
{
|
||||
u_char cb_type;
|
||||
u_char buf[256];
|
||||
u_char *bufp = buf;
|
||||
int len = 0;
|
||||
|
||||
cb_type = us->us_allowed & us->us_type;
|
||||
syslog(LOG_DEBUG, "cbcp_resp cb_type=%d", cb_type);
|
||||
|
||||
#if 0
|
||||
if (!cb_type)
|
||||
lcp_down(us->us_unit);
|
||||
#endif
|
||||
|
||||
if (cb_type & ( 1 << CB_CONF_USER ) ) {
|
||||
syslog(LOG_DEBUG, "cbcp_resp CONF_USER");
|
||||
PUTCHAR(CB_CONF_USER, bufp);
|
||||
len = 3 + 1 + strlen(us->us_number) + 1;
|
||||
PUTCHAR(len , bufp);
|
||||
PUTCHAR(5, bufp); /* delay */
|
||||
PUTCHAR(1, bufp);
|
||||
BCOPY(us->us_number, bufp, strlen(us->us_number) + 1);
|
||||
cbcp_send(us, CBCP_RESP, buf, len);
|
||||
return;
|
||||
}
|
||||
|
||||
if (cb_type & ( 1 << CB_CONF_ADMIN ) ) {
|
||||
syslog(LOG_DEBUG, "cbcp_resp CONF_ADMIN");
|
||||
PUTCHAR(CB_CONF_ADMIN, bufp);
|
||||
len = 3 + 1;
|
||||
PUTCHAR(len , bufp);
|
||||
PUTCHAR(5, bufp); /* delay */
|
||||
PUTCHAR(0, bufp);
|
||||
cbcp_send(us, CBCP_RESP, buf, len);
|
||||
return;
|
||||
}
|
||||
|
||||
if (cb_type & ( 1 << CB_CONF_NO ) ) {
|
||||
syslog(LOG_DEBUG, "cbcp_resp CONF_NO");
|
||||
PUTCHAR(CB_CONF_NO, bufp);
|
||||
len = 3;
|
||||
PUTCHAR(len , bufp);
|
||||
PUTCHAR(0, bufp);
|
||||
cbcp_send(us, CBCP_RESP, buf, len);
|
||||
(*ipcp_protent.open)(us->us_unit);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
cbcp_send(us, code, buf, len)
|
||||
cbcp_state *us;
|
||||
u_char code;
|
||||
u_char *buf;
|
||||
int len;
|
||||
{
|
||||
u_char *outp;
|
||||
int outlen;
|
||||
|
||||
outp = outpacket_buf;
|
||||
|
||||
outlen = 4 + len;
|
||||
|
||||
MAKEHEADER(outp, PPP_CBCP);
|
||||
|
||||
PUTCHAR(code, outp);
|
||||
PUTCHAR(us->us_id, outp);
|
||||
PUTSHORT(outlen, outp);
|
||||
|
||||
if (len)
|
||||
BCOPY(buf, outp, len);
|
||||
|
||||
output(us->us_unit, outpacket_buf, outlen + PPP_HDRLEN);
|
||||
}
|
||||
|
||||
static void
|
||||
cbcp_recvack(us, pckt, len)
|
||||
cbcp_state *us;
|
||||
char *pckt;
|
||||
int len;
|
||||
{
|
||||
u_char type, delay, addr_type;
|
||||
int opt_len;
|
||||
char address[256];
|
||||
|
||||
if (len) {
|
||||
GETCHAR(type, pckt);
|
||||
GETCHAR(opt_len, pckt);
|
||||
|
||||
if (opt_len > 2)
|
||||
GETCHAR(delay, pckt);
|
||||
|
||||
if (opt_len > 4) {
|
||||
GETCHAR(addr_type, pckt);
|
||||
memcpy(address, pckt, opt_len - 4);
|
||||
address[opt_len - 4] = 0;
|
||||
if (address[0])
|
||||
syslog(LOG_DEBUG, "peer will call: %s", address);
|
||||
}
|
||||
}
|
||||
|
||||
cbcp_up(us);
|
||||
}
|
||||
|
||||
extern int persist;
|
||||
|
||||
/* ok peer will do callback */
|
||||
static void
|
||||
cbcp_up(us)
|
||||
cbcp_state *us;
|
||||
{
|
||||
persist = 0;
|
||||
lcp_close(0, "Call me back, please");
|
||||
}
|
||||
@@ -1,26 +0,0 @@
|
||||
#ifndef CBCP_H
|
||||
#define CBCP_H
|
||||
|
||||
typedef struct cbcp_state {
|
||||
int us_unit; /* Interface unit number */
|
||||
u_char us_id; /* Current id */
|
||||
u_char us_allowed;
|
||||
int us_type;
|
||||
char *us_number; /* Telefone Number */
|
||||
} cbcp_state;
|
||||
|
||||
extern cbcp_state cbcp[];
|
||||
|
||||
extern struct protent cbcp_protent;
|
||||
|
||||
#define CBCP_MINLEN 4
|
||||
|
||||
#define CBCP_REQ 1
|
||||
#define CBCP_RESP 2
|
||||
#define CBCP_ACK 3
|
||||
|
||||
#define CB_CONF_NO 1
|
||||
#define CB_CONF_USER 2
|
||||
#define CB_CONF_ADMIN 3
|
||||
#define CB_CONF_LIST 4
|
||||
#endif
|
||||
@@ -1,33 +0,0 @@
|
||||
/*
|
||||
* chap.h - Challenge Handshake Authentication Protocol definitions.
|
||||
*
|
||||
* Copyright (c) 1995 Eric Rosenquist, Strata Software Limited.
|
||||
* http://www.strataware.com/
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms are permitted
|
||||
* provided that the above copyright notice and this paragraph are
|
||||
* duplicated in all such forms and that any documentation,
|
||||
* advertising materials, and other materials related to such
|
||||
* distribution and use acknowledge that the software was developed
|
||||
* by Eric Rosenquist. The name of the author may not be used to
|
||||
* endorse or promote products derived from this software without
|
||||
* specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* $Id: chap_ms.h,v 1.3 1997/08/19 17:52:35 peter Exp $
|
||||
*/
|
||||
|
||||
#ifndef __CHAPMS_INCLUDE__
|
||||
|
||||
#define MD4_SIGNATURE_SIZE 16 /* 16 bytes in a MD4 message digest */
|
||||
#define MAX_NT_PASSWORD 256 /* Maximum number of (Unicode) chars in an NT password */
|
||||
|
||||
void ChapMS __P((chap_state *, char *, int, char *, int));
|
||||
|
||||
#define __CHAPMS_INCLUDE__
|
||||
#endif /* __CHAPMS_INCLUDE__ */
|
||||
@@ -1,348 +0,0 @@
|
||||
/*
|
||||
* demand.c - Support routines for demand-dialling.
|
||||
*
|
||||
* Copyright (c) 1993 The Australian National University.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms are permitted
|
||||
* provided that the above copyright notice and this paragraph are
|
||||
* duplicated in all such forms and that any documentation,
|
||||
* advertising materials, and other materials related to such
|
||||
* distribution and use acknowledge that the software was developed
|
||||
* by the Australian National University. The name of the University
|
||||
* may not be used to endorse or promote products derived from this
|
||||
* software without specific prior written permission.
|
||||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*/
|
||||
|
||||
#ifndef lint
|
||||
static char rcsid[] = "$Id: demand.c,v 1.3 1997/08/19 17:52:36 peter Exp $";
|
||||
#endif
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <syslog.h>
|
||||
#include <netdb.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/wait.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/resource.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/socket.h>
|
||||
#ifdef PPP_FILTER
|
||||
#include <net/if.h>
|
||||
#include <net/bpf.h>
|
||||
#include <pcap.h>
|
||||
#endif
|
||||
|
||||
#include "pppd.h"
|
||||
#include "fsm.h"
|
||||
#include "ipcp.h"
|
||||
#include "lcp.h"
|
||||
|
||||
char *frame;
|
||||
int framelen;
|
||||
int framemax;
|
||||
int escape_flag;
|
||||
int flush_flag;
|
||||
int fcs;
|
||||
|
||||
struct packet {
|
||||
int length;
|
||||
struct packet *next;
|
||||
unsigned char data[1];
|
||||
};
|
||||
|
||||
struct packet *pend_q;
|
||||
struct packet *pend_qtail;
|
||||
|
||||
static int active_packet __P((unsigned char *, int));
|
||||
|
||||
/*
|
||||
* demand_conf - configure the interface for doing dial-on-demand.
|
||||
*/
|
||||
void
|
||||
demand_conf()
|
||||
{
|
||||
int i;
|
||||
struct protent *protp;
|
||||
|
||||
/* framemax = lcp_allowoptions[0].mru;
|
||||
if (framemax < PPP_MRU) */
|
||||
framemax = PPP_MRU;
|
||||
framemax += PPP_HDRLEN + PPP_FCSLEN;
|
||||
frame = malloc(framemax);
|
||||
if (frame == NULL)
|
||||
novm("demand frame");
|
||||
framelen = 0;
|
||||
pend_q = NULL;
|
||||
escape_flag = 0;
|
||||
flush_flag = 0;
|
||||
fcs = PPP_INITFCS;
|
||||
|
||||
ppp_send_config(0, PPP_MRU, (u_int32_t) 0, 0, 0);
|
||||
ppp_recv_config(0, PPP_MRU, (u_int32_t) 0, 0, 0);
|
||||
|
||||
#ifdef PPP_FILTER
|
||||
set_filters(&pass_filter, &active_filter);
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Call the demand_conf procedure for each protocol that's got one.
|
||||
*/
|
||||
for (i = 0; (protp = protocols[i]) != NULL; ++i)
|
||||
if (protp->enabled_flag && protp->demand_conf != NULL)
|
||||
if (!((*protp->demand_conf)(0)))
|
||||
die(1);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* demand_block - set each network protocol to block further packets.
|
||||
*/
|
||||
void
|
||||
demand_block()
|
||||
{
|
||||
int i;
|
||||
struct protent *protp;
|
||||
|
||||
for (i = 0; (protp = protocols[i]) != NULL; ++i)
|
||||
if (protp->enabled_flag && protp->demand_conf != NULL)
|
||||
sifnpmode(0, protp->protocol & ~0x8000, NPMODE_QUEUE);
|
||||
get_loop_output();
|
||||
}
|
||||
|
||||
/*
|
||||
* demand_discard - set each network protocol to discard packets
|
||||
* with an error.
|
||||
*/
|
||||
void
|
||||
demand_discard()
|
||||
{
|
||||
struct packet *pkt, *nextpkt;
|
||||
int i;
|
||||
struct protent *protp;
|
||||
|
||||
for (i = 0; (protp = protocols[i]) != NULL; ++i)
|
||||
if (protp->enabled_flag && protp->demand_conf != NULL)
|
||||
sifnpmode(0, protp->protocol & ~0x8000, NPMODE_ERROR);
|
||||
get_loop_output();
|
||||
|
||||
/* discard all saved packets */
|
||||
for (pkt = pend_q; pkt != NULL; pkt = nextpkt) {
|
||||
nextpkt = pkt->next;
|
||||
free(pkt);
|
||||
}
|
||||
pend_q = NULL;
|
||||
framelen = 0;
|
||||
flush_flag = 0;
|
||||
escape_flag = 0;
|
||||
fcs = PPP_INITFCS;
|
||||
}
|
||||
|
||||
/*
|
||||
* demand_unblock - set each enabled network protocol to pass packets.
|
||||
*/
|
||||
void
|
||||
demand_unblock()
|
||||
{
|
||||
int i;
|
||||
struct protent *protp;
|
||||
|
||||
for (i = 0; (protp = protocols[i]) != NULL; ++i)
|
||||
if (protp->enabled_flag && protp->demand_conf != NULL)
|
||||
sifnpmode(0, protp->protocol & ~0x8000, NPMODE_PASS);
|
||||
}
|
||||
|
||||
/*
|
||||
* FCS lookup table as calculated by genfcstab.
|
||||
*/
|
||||
static u_short fcstab[256] = {
|
||||
0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
|
||||
0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
|
||||
0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
|
||||
0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
|
||||
0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
|
||||
0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
|
||||
0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
|
||||
0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
|
||||
0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
|
||||
0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
|
||||
0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
|
||||
0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
|
||||
0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
|
||||
0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
|
||||
0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
|
||||
0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
|
||||
0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
|
||||
0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
|
||||
0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
|
||||
0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
|
||||
0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
|
||||
0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
|
||||
0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
|
||||
0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
|
||||
0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
|
||||
0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
|
||||
0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
|
||||
0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
|
||||
0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
|
||||
0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
|
||||
0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
|
||||
0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
|
||||
};
|
||||
|
||||
/*
|
||||
* loop_chars - process characters received from the loopback.
|
||||
* Calls loop_frame when a complete frame has been accumulated.
|
||||
* Return value is 1 if we need to bring up the link, 0 otherwise.
|
||||
*/
|
||||
int
|
||||
loop_chars(p, n)
|
||||
unsigned char *p;
|
||||
int n;
|
||||
{
|
||||
int c, rv;
|
||||
|
||||
rv = 0;
|
||||
for (; n > 0; --n) {
|
||||
c = *p++;
|
||||
if (c == PPP_FLAG) {
|
||||
if (!escape_flag && !flush_flag
|
||||
&& framelen > 2 && fcs == PPP_GOODFCS) {
|
||||
framelen -= 2;
|
||||
if (loop_frame(frame, framelen))
|
||||
rv = 1;
|
||||
}
|
||||
framelen = 0;
|
||||
flush_flag = 0;
|
||||
escape_flag = 0;
|
||||
fcs = PPP_INITFCS;
|
||||
continue;
|
||||
}
|
||||
if (flush_flag)
|
||||
continue;
|
||||
if (escape_flag) {
|
||||
c ^= PPP_TRANS;
|
||||
escape_flag = 0;
|
||||
} else if (c == PPP_ESCAPE) {
|
||||
escape_flag = 1;
|
||||
continue;
|
||||
}
|
||||
if (framelen >= framemax) {
|
||||
flush_flag = 1;
|
||||
continue;
|
||||
}
|
||||
frame[framelen++] = c;
|
||||
fcs = PPP_FCS(fcs, c);
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
|
||||
/*
|
||||
* loop_frame - given a frame obtained from the loopback,
|
||||
* decide whether to bring up the link or not, and, if we want
|
||||
* to transmit this frame later, put it on the pending queue.
|
||||
* Return value is 1 if we need to bring up the link, 0 otherwise.
|
||||
* We assume that the kernel driver has already applied the
|
||||
* pass_filter, so we won't get packets it rejected.
|
||||
* We apply the active_filter to see if we want this packet to
|
||||
* bring up the link.
|
||||
*/
|
||||
int
|
||||
loop_frame(frame, len)
|
||||
unsigned char *frame;
|
||||
int len;
|
||||
{
|
||||
struct packet *pkt;
|
||||
|
||||
/* log_packet(frame, len, "from loop: ", LOG_DEBUG); */
|
||||
if (len < PPP_HDRLEN)
|
||||
return 0;
|
||||
if ((PPP_PROTOCOL(frame) & 0x8000) != 0)
|
||||
return 0; /* shouldn't get any of these anyway */
|
||||
if (!active_packet(frame, len))
|
||||
return 0;
|
||||
|
||||
pkt = (struct packet *) malloc(sizeof(struct packet) + len);
|
||||
if (pkt != NULL) {
|
||||
pkt->length = len;
|
||||
pkt->next = NULL;
|
||||
memcpy(pkt->data, frame, len);
|
||||
if (pend_q == NULL)
|
||||
pend_q = pkt;
|
||||
else
|
||||
pend_qtail->next = pkt;
|
||||
pend_qtail = pkt;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* demand_rexmit - Resend all those frames which we got via the
|
||||
* loopback, now that the real serial link is up.
|
||||
*/
|
||||
void
|
||||
demand_rexmit(proto)
|
||||
int proto;
|
||||
{
|
||||
struct packet *pkt, *prev, *nextpkt;
|
||||
|
||||
prev = NULL;
|
||||
pkt = pend_q;
|
||||
pend_q = NULL;
|
||||
for (; pkt != NULL; pkt = nextpkt) {
|
||||
nextpkt = pkt->next;
|
||||
if (PPP_PROTOCOL(pkt->data) == proto) {
|
||||
output(0, pkt->data, pkt->length);
|
||||
free(pkt);
|
||||
} else {
|
||||
if (prev == NULL)
|
||||
pend_q = pkt;
|
||||
else
|
||||
prev->next = pkt;
|
||||
prev = pkt;
|
||||
}
|
||||
}
|
||||
pend_qtail = prev;
|
||||
if (prev != NULL)
|
||||
prev->next = NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* Scan a packet to decide whether it is an "active" packet,
|
||||
* that is, whether it is worth bringing up the link for.
|
||||
*/
|
||||
static int
|
||||
active_packet(p, len)
|
||||
unsigned char *p;
|
||||
int len;
|
||||
{
|
||||
int proto, i;
|
||||
struct protent *protp;
|
||||
|
||||
if (len < PPP_HDRLEN)
|
||||
return 0;
|
||||
proto = PPP_PROTOCOL(p);
|
||||
#ifdef PPP_FILTER
|
||||
if (active_filter.bf_len != 0
|
||||
&& bpf_filter(active_filter.bf_insns, frame, len, len) == 0)
|
||||
return 0;
|
||||
#endif
|
||||
for (i = 0; (protp = protocols[i]) != NULL; ++i) {
|
||||
if (protp->protocol < 0xC000 && (protp->protocol & ~0x8000) == proto) {
|
||||
if (!protp->enabled_flag)
|
||||
return 0;
|
||||
if (protp->active_pkt == NULL)
|
||||
return 1;
|
||||
return (*protp->active_pkt)(p, len);
|
||||
}
|
||||
}
|
||||
return 0; /* not a supported protocol !!?? */
|
||||
}
|
||||
@@ -1,71 +0,0 @@
|
||||
/*
|
||||
* ipxcp.h - IPX Control Protocol definitions.
|
||||
*
|
||||
* Copyright (c) 1989 Carnegie Mellon University.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms are permitted
|
||||
* provided that the above copyright notice and this paragraph are
|
||||
* duplicated in all such forms and that any documentation,
|
||||
* advertising materials, and other materials related to such
|
||||
* distribution and use acknowledge that the software was developed
|
||||
* by Carnegie Mellon University. The name of the
|
||||
* University may not be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
|
||||
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* $Id$
|
||||
*/
|
||||
|
||||
/*
|
||||
* Options.
|
||||
*/
|
||||
#define IPX_NETWORK_NUMBER 1 /* IPX Network Number */
|
||||
#define IPX_NODE_NUMBER 2
|
||||
#define IPX_COMPRESSION_PROTOCOL 3
|
||||
#define IPX_ROUTER_PROTOCOL 4
|
||||
#define IPX_ROUTER_NAME 5
|
||||
#define IPX_COMPLETE 6
|
||||
|
||||
/* Values for the router protocol */
|
||||
#define IPX_NONE 0
|
||||
#define RIP_SAP 2
|
||||
#define NLSP 4
|
||||
|
||||
typedef struct ipxcp_options {
|
||||
int neg_node : 1; /* Negotiate IPX node number? */
|
||||
int req_node : 1; /* Ask peer to send IPX node number? */
|
||||
|
||||
int neg_nn : 1; /* Negotiate IPX network number? */
|
||||
int req_nn : 1; /* Ask peer to send IPX network number */
|
||||
|
||||
int neg_name : 1; /* Negotiate IPX router name */
|
||||
int neg_complete : 1; /* Negotiate completion */
|
||||
int neg_router : 1; /* Negotiate IPX router number */
|
||||
|
||||
int accept_local : 1; /* accept peer's value for ournode */
|
||||
int accept_remote : 1; /* accept peer's value for hisnode */
|
||||
int accept_network : 1; /* accept network number */
|
||||
|
||||
int tried_nlsp : 1; /* I have suggested NLSP already */
|
||||
int tried_rip : 1; /* I have suggested RIP/SAP already */
|
||||
|
||||
u_int32_t his_network; /* base network number */
|
||||
u_int32_t our_network; /* our value for network number */
|
||||
u_int32_t network; /* the final network number */
|
||||
|
||||
u_char his_node[6]; /* peer's node number */
|
||||
u_char our_node[6]; /* our node number */
|
||||
u_char name [48]; /* name of the router */
|
||||
int router; /* routing protocol */
|
||||
} ipxcp_options;
|
||||
|
||||
extern fsm ipxcp_fsm[];
|
||||
extern ipxcp_options ipxcp_wantoptions[];
|
||||
extern ipxcp_options ipxcp_gotoptions[];
|
||||
extern ipxcp_options ipxcp_allowoptions[];
|
||||
extern ipxcp_options ipxcp_hisoptions[];
|
||||
|
||||
extern struct protent ipxcp_protent;
|
||||
@@ -1 +0,0 @@
|
||||
int decode(FILE *fd, char *buffer);
|
||||
Reference in new issue
Block a user