I just cooked up this script the other day because I was tired of repeatedly changing file extensions and tar-ing all of the gerbers and drill files for upload.
originally it was supposed to be a simple `change the extensions’ quicky, but like most of my projects I went overboard and added some extra handy features, so
prepping for upload should be pretty much automated in most cases (i.e. my case)
Prerequisites: Linux, gEDA pcb, perl.
Features: This script changes all of the output gerber file extensions to those meeting BatchPCB [criteria
If there are two drill files present (for example project.unplated-drill.cnc and project.plated-drill.cnc) this script will merge the two files in proper NC drill file format for upload. it will then compress the output files into a *.tgz ready to be uploaded to bPCB.
limitations: currently, this script is designed only for 2 layer boards (front, frontmask, back, backmask, silk screen, and drill file) and can only perform merges on up to 2 drill files. (if any of this is a problem, learn some perl and modify it to your liking)
I just figured I’d post it here and hope that someone else could get some use out of it.
#!/usr/bin/env perl
################################################################################
# batchup.pl is a perl script that got out of hand for prepping gerber files
# output by gEDA pcb for upload to batchpcb.com. It first takes the pertinent
# files in the project directory, changes the file extensions to fit batchpcb
# criteria, if there are two .cnc drill files, it will merge them together
# it will then pack the whole mess up into a *.tar.gz ready for upload.
################################################################################
use strict;
use warnings;
use File::Copy;
use File::Basename;
use Archive::Tar;
################################################################################
# cncmerge is a subroutine for mergeing the differences between 2 cnc format
# drill files into one file. this is because batch pcb will only allow the up-
# load of one cnc file in the archive.
################################################################################
sub cncmerge
{
#locals
my @files = @_;
my $fhone;
my $fhtwo;
my $fhoutput;
my $fileone = $files[0];
my $filetwo = $files[1];
my $fileout = "drillfile.cnc";
#open input files and read lines into arrays
#then open the output file for merge.
open($fhone,"<",$fileone) or die "couldn't open file $!";
my @onelines = <$fhone>;
open($fhtwo,"<",$filetwo) or die "couldn't open file $!";
my @twolines = <$fhtwo>;
open($fhoutput,">>",$fileout) or die " couldn't make output file $!";
#print out the first 2 lines of the header M48, which is the header start
#and INCH, which marks the units.
print $fhoutput "$onelines[0]";
print $fhoutput "$onelines[1]";
#initialize iteration indexes to start at beginning of header info.
my $startdex1 = my $startdex2 = 2;
#write header info from file one to merged file
while($onelines[$startdex1] !~ m/%/)
{
print $fhoutput "$onelines[$startdex1]";
$startdex1 ++;
}
#write header info from file two to merged file.
while($twolines[$startdex2] !~ m/%/)
{
print $fhoutput "$twolines[$startdex2]";
$startdex2 ++;
}
#print the header end '%' to file and kick up the counters 1
print $fhoutput "$twolines[$startdex2]";
$startdex1++;
$startdex2++;
#write all of the body information to the merge file.
while($onelines[$startdex1] !~ m/M30/)
{
print $fhoutput "$onelines[$startdex1]";
$startdex1 ++;
}
while($twolines[$startdex2] !~ m/M30/)
{
print $fhoutput "$twolines[$startdex2]";
$startdex2 ++;
}
#print 'M48' file end marker
print $fhoutput "$twolines[$startdex2]";
#close filehandles
close($fhone);
close($fhtwo);
close($fhoutput);
}
my $dir = ".";
my $dirhandle;
my $outdir = "UPLOAD";
my $outdirhandle;
#open current directory.
opendir($dirhandle,$dir);
#create an array of gerber files
my @gerbers = grep {m/.gbr$/} readdir($dirhandle);
closedir($dirhandle);
#reopen dir and create an array of drill files.
opendir($dirhandle,$dir);
my @drills = grep {m/.cnc$/} readdir($dirhandle);
#make a directory to store the results
if (!-d $outdir)
{
mkdir($outdir) or die "couldn't create directory $!";
}
#rename gerber files appropriately and move to $outdir
foreach(@gerbers)
{
my $newfile = $_;
my $copy;
if(m/\.front\./)
{
$newfile =~ s/.gbr/.top/;
$copy = 1;
}
elsif(m/\.frontmask\./)
{
$newfile =~ s/.gbr/.tsm/;
$copy = 1;
}
elsif(m/\.back\./)
{
$newfile =~ s/.gbr/.bot/;
$copy = 1;
}
elsif(m/\.backmask\./)
{
$newfile =~ s/.gbr/.bsm/;
$copy = 1;
}
elsif(m/\.frontsilk\./)
{
$newfile =~ s/.gbr/.slk/;
$copy = 1;
}
else
{
$copy = undef;
}
if($copy)
{
copy("$_","$outdir/$newfile")
or die "couldn't copy file $!";
}
}
# Handle Drill files, with merge between unplated and plated.
my $drillfile;
#only one drill file
if(scalar(@drills) == 0)
{
print("No drill file found, proceeding anyway.\n");
}
elsif (scalar(@drills) == 1)
{
$drillfile = $drills[0];
copy("$drillfile","$outdir/$drillfile")
or die "Couldn't copy drill file $!";
}
#if plated and unplated perform a merge on the two files.
elsif(scalar(@drills) == 2)
{
$drillfile = "drillfile.cnc";
&cncmerge(@drills);
move("$drillfile","$outdir/$drillfile")
or die "Couldn't copy drill file $!";
}
#too lazy to handle more than two files, shouldn't need to.
else
{
print "there are > 2 drill files, requires manual merge.\n";
}
#list files in outdir and prepare for archiving.
opendir($outdirhandle,$outdir);
my @modgerber = readdir($outdirhandle);
my @files_tar;
print "the following files have been archived: \n";
foreach(@modgerber)
{
#add to array if not a dotfile or a previously generated archive.
if(!($_ eq "." || $_ eq ".." || $_ eq "output.tgz"))
{
print "\t$_\n";
push(@files_tar,$_);
}
}
#go in and archive this sucker up!
chdir($outdir);
Archive::Tar->create_archive('output.tgz', COMPRESS_GZIP, @files_tar) or die "what the hell $!";
print("Files Archived in output.tgz\n");
#and just for fun, delete all of the copied files.
foreach(@files_tar)
{
unlink($_) or die "couldn't delete stupid files $!";
}
print("Temporary files are deleted. please ensure all files in list are g2g!\n");
#close filehandles
closedir($outdirhandle);
closedir($dirhandle);
](OSH Park ~)