Saturday, August 18, 2012
Advanced Arduino Hacking
The Pragmatic Bookshelf | PragPub April 2011 | Advanced Arduino Hacking:
Monday, September 12, 2011
Searching code for a string not in the comments...
>cat example.txt
token asdf asdf @OK
asdf token asdf @OK
//token @BAD
asdf token asdf // asdf token asdf @OK
// This is a token @BAD
/some/dir/token @OK
aaa token try again @OK
aaa token try again @OK
aaaa token try again @OK
>egrep '^.?([^/][^/])*token' example.txt
token asdf asdf @OK
asdf token asdf @OK
asdf token asdf // asdf token asdf @OK
aaaatoken try again @OK
aaa token try again @OK
aaaa token try again @OK
Thursday, April 21, 2011
USB3 Speeds
COUNTERPOINT
by Chris Karr, Director, Software/Firmware Engineering of the Branded Products Group at Western Digital Corporation (and previous author of SpeedTools (QuickBench, ZoneBench, etc.),
I read your article and have some feedback about your Key Insight #1. I strongly disagree that USB 3.0 is slower than eSATA, per se. eSATA is limited to 3 Gb/sec whereas USB 3.0 is a 5 Gb/sec interface. They both use 8b/10b encoding so they are both 80% efficient on paper. (Transport protocol overhead further reduces real world data transfer rates and this overhead varies by bus interface type.) We expect USB 3.0 to be able to crack 400 Megabinary bytes per second (MiB/sec) with the right setup. eSATA will likely never crack 275 MiB/sec unless/until they move to 6 Gb.
The limiting factor with USB 3.0 storage devices to date has been the 3 Gb SATA backend of the first generation of USB 3.0 to SATA bridge chips. The 3 Gb SATA interface limits the potential of the 5 Gb Superspeed USB interface. Plus, converting from SATA protocol to USB protocol adds a bit of additional overhead.
That said, there are two basic approaches to actually deliver max speed over USB SuperSpeed with a bridged SATA solution, neither of which, to my knowledge, have yet been done:
1) Put two 3 Gb SATA ports on the back end of the USB bridge and connect two SATA devices which can saturate both of the SATA busses (think two SandForce-based SSD's in a RAID 0).
2) Make a bridge chip with a USB 3.0 front end and a 6 Gb SATA backend and stuff a 500 MiB/sec enterprise-class 6 Gb SSD or RAM drive behind it.
You will need a very powerful PCI bus (aka Gen 2 running off north-bridge, etc.) to get the best numbers, but we believe USB 3.0 can reach at least 400 MiB/sec once the other system bottlenecks are resolved. Of course, with a single HDD all this comparison stuff doesn’t mean much because they just aren’t fast enough to be meaningfully bottlenecked by either SATA or SuperSpeed USB.
Lastly, look for well-designed integrated USB 3.0 host controllers coming in the near future to further boost USB max data transfer rates.
Wednesday, April 6, 2011
Preserving code formatting in blog posts
http://www.manoli.net/csharpformat/
Vim Visual Selection Tricks
# VISUAL SELECTION TRICKS:
# You can use filters and vim's execution mode.to do some powerful things.
# A filter is any standard UNIX program (sort, awk, grep, cut, paste, sed ...) that can read from stdin and write to stdout.
# Vim's execution mode lets you read in or replace text with the output of a program. If you make a visual selection (say,
# using V or C-V), and hit :, your command prompt will immediately be :'<,'>, which means "Apply whatever command follows
# to the lines included in the visual selection." At this point, you can write !foo to replace the text with the output of
# program foo.
# For example, to sort the text by the python column, select it, hit :, and enter !sort -k5. The whole command will look like
:'<,'>!sort -k5
# Running it will produce:
a b cd 1 p
b b cd 2 y
c b cd 3 t
d b cd 4 h
# Results in:
d b cd 4 h
a b cd 1 p
c b cd 3 t
b b cd 2 y
# For more complex tasks, awk is your friend. A command like
:'<,'>!awk '{ print $1, $3, $2, $4, $5 }'
a cd b 1 p
b cd b 2 y
c cd b 3 t
d cd b 4 h
# will flip the second and third columns (but note that inter-column spacing is collapsed).
# To do maths on a column, try something like
:'<,'>!awk '{ sub($4, $4*2+1); print }'
a b cd 3 p
b b cd 5 y
c b cd 7 t
d b cd 9 h
# Could get the same result with perl if there is only one column of numbers:
:'<,'>!perl -pe 's/\d+/$&*2+1/e'
# To flip the visual selection just select the rows and then:
:'<,'>!tac
d b cd 4 h
c b cd 3 t
b b cd 2 y
a b cd 1 p
# This pipes the lines through the unix 'reverse cat' program.
Saturday, March 5, 2011
My switch from the 3Gs iPhone to Android (Samsung EPIC on Sprint)
- Physical keyboard (although I am also very impressed with Swype)
- Front facing camera which will allow for video conferencing
- At least a 1Ghz processor (The GPU helps out a lot as well)
- AMOLED screen (Not technically a requirement but if you have ever seen it you will understand)
- Android OS 2.2 (Froyo) -- Sprint actually just retracted this update but it should be back soon.
- Faster network (4G)
- Stop paying any more Apple taxes
- The network just seems much much snappier than AT&T even when I am on 3G.
- The screen is amazing when I set it next to my old phone the iPhone seems downright dull. When I look at my Picasa pictures on the EPIC using there "gallery" app it is like looking at the pictures for the first time. I have never seen my pictures looking so good!
- Integration with all the Google tools is excellent.
- Swype virtual keyboard is much more usable than I ever thought it could be. It makes me question my requirement for a physical keyboard it is that good. If you are not planning to write scripts on your phone you may really not need the physical keyboard, maybe.
- The keyboard keys are a little bit too flush. I wish everyone that made physical keyboards would use the raised keys like on Blackberry's. I find myself looking at the keys a bit too much trying to find where my fingers are exactly. I was thinking about adding a dot of super glue to all the keys so that I could really feel them but I am not sure there is enough clearance.
- I wish the four buttons at the bottom of the phone were physical keys as well so I wouldn't have to look at them to push them.
- I find it a bit frustrating to get help with things. For instance one of the reasons I got the phone was so that I could send certain incoming calls directly to voice mail (you know who you are, jk :). If you search the intertubes you can find lots of people talking about it, but it seems like my phone does not have the option. I am not sure if it is the Android OS 2.1 or Sprints front end or what but the slight differences are a bit frustrating. On the other hand I know that eventually I will get it working where as with the iPhone I would never be able to fix it because of the closed nature of the phone.
Tuesday, May 25, 2010
Is DropBox a usefull tool?
Saturday, May 8, 2010
Chaning startup programs on windows 7
NOTE: Using the Selective Startup option in System Configuration (msconfig), you can enable or disable startup programs. You will need to be logged into an administator account, or provide the administrator password to open System Configuration.
1. Open the Start Menu.A) In the search line, type msconfig and press Enter. (See screenshot below)ORB) Go to step 3.
2. Open the Control Panel (All items view) and click on the Administrative Tools icon, then click on System Configuration. Close the Control Panel and Administrative Tools windows.
3. If prompted, click on Continue for the UAC prompt, or type in the administrator's password.
4. Click on the Startup tab. (See screenshot below)Tip
If you look under the Location column for the Start Item, you will see the registry location for it that you can use to remove the startup item using METHOD FOUR below instead.5. To Disable a Startup Program -A) Select a listed startup program and uncheck it. (See screenshot above)6. To Enable a Startup Program -
B) Repeat to disable anymore listed startup programs.A) Select a listed startup program and check it. (See screenshot below step 4)7. To Disable All Listed Startup Programs -
B) Repeat to enable anymore listed startup programs.A) Click on the Disable all button. (See screenshot below step 4)8. To Enable All Listed Startup Programs -
B) Go to step 9.A) Click on the Enable all button. (See screenshot below step 4)9. Click on Apply. (See screenshot below step 4)
10. Click on the Boot tab, then check the Make all boot settings permanent box and click on OK. (See screenshot below)11. Click on Yes. (See screenshot below)12. Click on the Restart button to apply. (See screenshot below)
WARNING: This will restart your computer immediately. Save and close anything that you are working on first.
Monday, March 29, 2010
VIM TIPS
PERFORCE TIPS:
# PERFORCE SHORTCUTS
alias p4_client echo `p4 info | perl -ne 's/Client name: (.*)$/print $1/e'`
alias p4_changes p4 changes -c `p4_client`
Monday, January 18, 2010
Microsoft is sooo 1980s....
Thursday, October 29, 2009
Friday, September 25, 2009
How to colorize any text based output
http://winterstorm.ca/hilite
Wednesday, September 23, 2009
Extract prices from craiglist
# This is a script that will help me search craigslist and extract
# price information and average the data to get what the going
# price of an item is
#
# Example:
#; ~/bin/cl_get_prices.pl -string=2006 -string=maxima
#; ~/bin/cl_get_prices.pl -string=2003 -string=maxima -cities=dallas
#; ~/bin/cl_get_prices.pl -string=2003 -string=maxima -verb=4
#; ~/bin/cl_get_prices.pl -string=ps3 -string=80gb -verb=4
#; ~/bin/cl_get_prices.pl -string=ps3 -string=80gb -trim=.333
#; ~/bin/cl_get_prices.pl -string=ps3 -string=60gb -trim=.2 -filter_on_title=1
#
# I think I am going to give three outputs. Mean, Median and Trimmed Mean.
# This way if there is outlier data it will be easy to spot in the Mean
# value.
use strict;
use Getopt::Long;
use List::Util qw(sum);
use Statistics::Descriptive;
use List::MoreUtils qw(uniq);
my @item_prices;
my $delay_between_searches = 5;
# Define the arguments
my %opts = ();
&usage unless &GetOptions(\%opts, 'help'
,'strings=s@'
,'cities=s@'
,'trim=s'
,'filter_on_title=s'
,'min=s'
,'max=s'
,'verbosity=i'
);
if ( @{opts{strings}} eq 0 ) { die " NO SEARCH STRING WAS GIVEN"; }
unless ( exists ${opts{cities}} ) {
push( @{$opts{cities}}, 'austin' );
}
$opts{trim} = .25 unless ( exists $opts{trim} );
$opts{min} = "" unless ( exists $opts{min} );
$opts{max} = "" unless ( exists $opts{max} );
$opts{verbosity} = 3 unless ( exists $opts{verbosity} );
foreach my $city ( @{$opts{cities}} ) {
&get_item_prices( \@item_prices, \@{$opts{strings}}, $city, $opts{min}, $opts{max}, $opts{filter_on_title} );
sleep( $delay_between_searches );
}
@item_prices = sort {$a <=> $b } @item_prices;
@item_prices = uniq @item_prices;
my $stat = Statistics::Descriptive::Full->new();
$stat->add_data(@item_prices);
$Statistics::Descriptive::Tolerance = 1e-10;
my $mean = $stat->mean();
my $var = $stat->variance();
my $tm = $stat->trimmed_mean($opts{trim});
my $std = $stat->standard_deviation();
print "Prices: @item_prices\n";
printf "Statistics: Mean: %10.4f Var: %10.4f Std Dev: %10.4f Trimmed mean: %10.4f\n", $mean, $var , $std , $tm ;
print "". scalar( @item_prices ) . " ITEMS WERE FOUND\n";
print "lowest:\t\t$item_prices[0]\n";
print "highest:\t$item_prices[$#item_prices]\n";
print "Mean:\t\t" . sum( @item_prices )/@item_prices ."\n";
print "Median:\t\t" . $item_prices[@item_prices/2] ."\n";
print "Trim Mean:\t" . $tm ."\n";
sub get_item_prices {
my ( $item_prices_ref, $strings_ref, $city, $min, $max, $filter_on_title ) = @_;
my $wget="http://$city.craigslist.org/search/sss?query=";
my $str_cat = "";
foreach my $str ( @$strings_ref ) {
$wget .= "$str_cat$str";
$str_cat = "+";
}
my $html = `wget -q -O - $wget`;
print $html . "\n" if $opts{verbosity} > 6;
my @chunks = split /(<\/?p>\s*)+/,$html;
# Filter out everything but the titles
my $num_chunks = scalar @chunks;
for ( my $idx = $num_chunks-1; $idx >= 0; $idx-- ) {
delete $chunks[$idx] unless $chunks[$idx] =~ m/^......\s-\s/;
print "$idx|$chunks[$idx]\n" if $opts{verbosity} > 4;
}
# Clean up the title and do additional filtering on the title
my $num_chunks = scalar @chunks;
for ( my $idx = $num_chunks-1; $idx >= 0; $idx-- ) {
my $rm_item = 0;
$chunks[$idx] =~ s/^.+html">//;
$chunks[$idx] =~ s/>//gs;
$chunks[$idx] =~ s/<//gs;
$chunks[$idx] =~ s/ / /gs;
$chunks[$idx] =~ s/<[^>]*>//gs;
if ( $filter_on_title eq "1" ) {
foreach my $str ( @$strings_ref ) {
if ( $chunks[$idx] !~ m/$str/i ) {
$rm_item = 1;
}
}
}
delete $chunks[$idx] unless $rm_item == 0;
}
# Extract price information from the titles
@chunks = sort @chunks;
foreach my $chunk (@chunks) {
if ( $chunk ne "" ) {
print " $chunk\n" if $opts{verbosity} > 3;
my @words = split(' ', $chunk);
foreach my $word (@words) {
if ( $word =~ m/^\$/) {
$word =~ s/(\$|,)//g ;
if ( $word =~ m/^\d+$/ ) {
push(@$item_prices_ref, $word);
}
}
}
}
}
}
Wednesday, June 10, 2009
HOTO: Create html "snapshot" from your gvim editor
The function is not working.. :( will have to work on it more later...
" Settings for :TOhtml
let html_number_lines=1
let html_use_css=1
let use_xhtml=1
""function not working
"function! MyToHtml()
" normal :colorscheme default
" normal :TOhtml
" normal :colorscheme torte
"endfunction
"nmap <Leader>html :call MyToHtml()
nmap <Leader>html :TOhtml<CR>zR :w! ~/tmp/<C-R>%<CR> :q!<CR>
nmap <Leader>print :colorscheme default<CR> :TOhtml<CR>zR :w! ~/tmp/<C-R>%<CR> :q!<CR>zR:colorscheme torte<CR>
Monday, June 8, 2009
COLRM - Discovered a fun new tool!
Here is an example where I removed columns 87 to the end and from column 1 to 69 leaving just column data from 70 to 86:
> cat ~/tmp/max_data.out colrm 87 colrm 1 69 > ~/tmp/max_data2.out
Friday, June 5, 2009
A better unit conversion script (h2b b2h h2d d2h)
I also have some vim commands that call this script and allow me to do do conversions right from within vim (will add this vim code later). I also have some csh alias commands that I will add later as well.
It has proven to be very powerful and has improved my coding and debugging efficiency. Hope someone else finds it useful.
##### FILE: bc_conversion.pl ######
#!/usr/local/bin/perl -w
# Use the bc function to do conversions..
#
## | check if called properly
#if ($#ARGV >= 0) {
if ($#ARGV < 2) {
print " Usage: $0\n" ;
print " used to wrap bc so you can set the base input and output \n" ;
print " in order to do conversions. For example to convert binary \n" ;
print " to hex, run the following command: \n" ;
print " bc_wrapper.sh 2 16 1001_1011 \n" ;
print " RESULT: 9B \n" ;
exit
}
$ARGV[2] =~ s/_//g;
$ARGV[2] =~ tr/a-z/A-Z/;
# The following is a csh command that tells the tool bc the output base type,
# the input base type and the expression to run.
my $cmd = "bc << EOF \
obase=$ARGV[1]; \
ibase=$ARGV[0]; \
$ARGV[2]; \
quit; \
EOF";
#print " $cmd \n";
#system("$cmd") == 0 or die "system $cmd failed: $?";
my $result = `$cmd`;
# Make the result easier to read by inserting underscores
if ( ( $ARGV[1] eq "2" ) || ( $ARGV[1] eq "16" ) ) {
$result = reverse $result;
$result =~ s/(\w{4})/$1_/g;
$result = reverse $result;
$result =~ s/^_//g;
}
print "$result";
My faster little find script
##### FILE: find.pl #####
#!/usr/local/bin/perl -w
use strict;
use Getopt::Long;
use Pod::Usage;
my $cmdLine = "rerunRegressionResults.pl @ARGV \n";
my $dateStamp=`date +'%Y-%m-%d-%H%M'`; chomp($dateStamp);
my $output = "";
my $help = 0;
my $grep = "";
my $displayOnly = 0;
my $noGrep = 0;
my $noVim = 0;
my $vimCmd = "";
my $dryRun = 0;
my $cmd = "";
my @fileNames;
my $replaceWithSpace = "~"; # Default is to replace all ~ with spaces.
my $arg = "";
my $verbosity = "";
my $endFind = "";
my @strings;
my $grepArg = "";
my $findRslt = "";
my $findRsltFound = 0;
my $endGrep = "";
my @dirs;
my @findRslts;
my @nots;
my @ands;
my @prunes;
my @sqlResults;
my @outputList;
my $ok = GetOptions(
'displayOnly|do' => \$displayOnly,
'noVim|nv' => \$noVim,
'vimCmd|vc=s' => \$vimCmd,
'dryRun|dr' => \$dryRun,
'dirs=s@' => \@dirs,
'output=s' => \$output,
'endGrep|eg=s' => \$endGrep,
'fileNames|fn=s@' => \@fileNames,
'noGrep|ng' => \$noGrep,
'arg=s' => \$arg,
'verbosity=s' => \$verbosity,
'endFind|ef=s' => \$endFind,
'strings=s@' => \@strings,
'grepArg|ga=s' => \$grepArg,
'nots=s@' => \@nots,
'ands=s@' => \@ands,
'prunes=s@' => \@prunes,
'replaceWithSpace=s' => \$replaceWithSpace,
'help' => \$help
);
if ( !$ok ) { die; }
pod2usage(1) if $help;
push ( @strings , @ARGV );
if ( ( @strings == 0 ) && ( @fileNames == 0 ) ) { die " NO SEARCH STRING OR FILE NAME GIVEN!!! "; }
# Decide the defaults:
if ( @fileNames == 0 ) {
$fileNames[0] = "*";
} else {
if ( @strings == 0 ) { $strings[0] = $fileNames[0]; }
}
if ( @dirs == 0 ) {.
$dirs[0] = "$ENV{'PWD'}";.
}
if ( $vimCmd eq "" ) { $vimCmd = "/usr/local/bin/gvim"; }
if ( $arg eq "" ) { $arg = ""; }
if ( $endFind eq "" ) { $endFind = ""; }
#if ( $grepArg eq "" ) { $grepArg = " -n -I -i -C 3 "; }
if ( $grepArg eq "" ) { $grepArg = " -n -I -i "; }
if ( $output eq "" ) { $output = "~/tmp/find_$strings[0].rslt" }
# Start to build up the find argument
foreach ( @prunes ) { $arg .= " -not \\( -type d -name \"*$_*\" -prune \\) " }
foreach ( @ands ) { $arg .= " -name \"*$_*\" " }
foreach ( @nots ) { $arg .= " -not -name \"*$_*\" " }
if ( @fileNames > 1 ) { $arg .= " \\( "; }
foreach my $index (0..$#fileNames) {
if ( $index > 0 ) { $arg .= " -o "; }
$arg .= " -name \"*$fileNames[$index]*\" ";
}
if ( @fileNames > 1 ) { $arg .= " \\) "; }
# Create the comands and execute
foreach my $string ( @strings ) {
if ( $replaceWithSpace ne "" ) { $string =~ s/$replaceWithSpace/ /g; }
$cmd = "find @dirs $arg $endFind -follow ";
$cmd .= " -print0 | xargs -0 grep $grepArg '$string' $endGrep" unless $noGrep;
print " $cmd \n" unless $verbosity eq "quiet";
$findRslt = qx"$cmd" unless ( $dryRun );
if ( $findRslt =~ m/[a-z]/i ) {
$findRsltFound++;
push ( @outputList , $findRslt );
}
}
if ( ( $findRsltFound < 1 ) && ( ! $dryRun ) ) {.
die " !ERROR! ---> \"$strings[0]\" not found in dir(s) @dirs \n";.
}
# Generate my output
if ( $displayOnly ) {
print @outputList;
} else {
open OUT_FILE, "> $output" or die "cant open $output : $!";
print OUT_FILE @outputList;
close OUT_FILE;
#print @outputList;
unless ( $noVim ) {
my $cmd3;
my $gvimSearch = "";
# The search +/ does not work if using --remote in vim!!! SUCKS
$gvimSearch = " +\"/$strings[0]\" " unless ( $vimCmd =~ m/remote/ );
$cmd3 = "csh -c \"$vimCmd $output $gvimSearch \"";
print " $cmd3 \n";
system("$cmd3") == 0 or die "system $cmd3 failed: $?" unless ( $dryRun );
}
}
__END__
=head1 NAME
find.pl help
=head1 SYNOPSIS
find [options]
Options:
-help This help message
-dirs Directory to search*
-output Alternative output filename
-type Find's type (default = "-type f")
-endGrep|eg Additional grep arguments
-fileNames|fn File Name (default = "*")
-arg Additional find Arguments
-endFind|ef Additional find Arguments for the end of find command
-strings Strings grep will use to search*
-grepArg|ga Alternative grep arguments (default = " -n -I -i -C 3 ")
-nots Additional find logic*
-ands Additional find logic*
-prunes Trims directories from search
-displayOnly|do Does not generate a file
-fno Search for the file name only (no grep)
-noVim|nv Do not open output file with vim
-dryRun|dr Run the script but print the commands do not actually run them
Examples:
find.pl stringtofind
find.pl -fn filetofind stringtofind
find.pl -string stringtofind -fa "-maxdepth 1"
find.pl -s stringtofind -fa "-maxdepth 1"
find.pl stringtofind -fa "-maxdepth 1"
find.pl stringtofind -prune directorynottosearch
find.pl stringtofind -not log
find.pl string_with_spaces -replaceWithSpace _
=cut
Faster editting of linux script files
##### FILE: vich.pl #####
#!/usr/local/bin/perl -w
use strict;
my $whichOutput = qx` which $ARGV[0]; `;
$whichOutput =~ s/\s+$//;
stat($whichOutput);
print "Readable\n" if -r _;
print "Writable\n" if -w _;
print "Executable\n" if -x _;
print "Setuid\n" if -u _;
print "Setgid\n" if -g _;
print "Sticky\n" if -k _;
print "Text\n" if -T _;
print "Binary\n" if -B _;
if ( ( $whichOutput =~ m/^\// ) && ( -T $whichOutput ) ) {
qx`gvim -geometry 100x50 $whichOutput `;
} else {
my $myoutput = "~/tmp/vich.out";
open OUT_FILE, "> $myoutput" or die "cant open $myoutput : $!";
print OUT_FILE $whichOutput;
close OUT_FILE;
qx`gvim -geometry 100x50 $myoutput `;
}
##########################################
# END OF FILE
##########################################
Make an alias:
> alias vich vich.pl
Now instead of doing:
> which myscript
/usr/bin/myscript
> vim /usr/bin/myscript
you can just do:
> vich myscript
Just a little thing to speed things up..
Make your config files very flexible (w/ Perl eval)
Most of the code was taken from:
http://www.usenix.org/publications/perl/perl13.html
Here is my proof of concept code:
##### FILE: evalConfigExample.pl #####
#!/usr/bin/perl -w
# Filename: evalConfigFileExample.pl
# This is a proof of concept script to show how one can use a perl script as a config.
# file. This allows much more freedom when declaring a configuration file. One can
# call functions, redefine functions and generally do anything that you could.
# normally do in a regular perl script. Ex:
#; ~/bin/evalConfigFileExample.pl -file ~/bin/evalConfigFileExample.cfg
use Getopt::Long;
use Data::Dumper;
use Pod::Usage;
my $page_info ;
my %opts = ();
my $ok = GetOptions(\%opts,
'file=s',
'help'
);
if ( !$ok ) { die; }
pod2usage(1) if (exists ( $opts{help} ) );
sub printer {
print "In Perl prog\n";
}
sub hello_world {
print "Calling hello_world from eval'd config file!\n";
}
sub parse_cfg {
my($file) = @_;
delete($INC{$file});
eval('require("$file")');
die "*** Failed to eval() file $file:\n$@\n" if ($@);
print ("VENDOR = $VENDOR \n");
}
printer();
parse_cfg( $opts{file} );
print ("VENDOR = $VENDOR \n");
printer();
##########################################
# END OF FILE
##########################################
##### FILE: evalConfigExample.cfg #####
#evalConfigFileExample.cfg
$VENDOR = "Sun";
$HARDWARE = "Sparc";
$OS = "Solaris";
$VERSION = "2.5";
$HOSTNAME = `/bin/hostname`;
$PSCMD = "/usr/bin/ps -ef";
hello_world();
sub printer {
print "In required file\n";
}
##########################################
# END OF FILE
##########################################
The output should look like this:
> evalConfigFileExample.pl -file evalConfigFileExample.cfg
In Perl prog
Subroutine printer redefined at evalConfigFileExample.cfg line 9.
Calling hello_world from eval'd config file!
VENDOR = Sun
VENDOR = Sun
In required file