+sub Punch {
+ if (!defined($::client_id)) {
+ print "You must first ``connect''.\n";
+ return;
+ }
+
+ my $id = shift;
+ my $start = shift;
+ my $count = shift;
+
+ if (!defined($id) || scalar($id) < 1 || !defined($start) ||
+ scalar($start) < 0 || !defined($count) || scalar($count) < 0) {
+ print "invalid arguments; type \"help punch\" for a synopsis\n";
+ return;
+ }
+
+ print("Punching $count bytes starting at byte $start in object $id...\n");
+
+ my $obdo;
+ $obdo->{id} = $id;
+
+ # the perl we're using doesn't support pack type Q
+ my $packed = pack("L", $::client_id) . obdo_pack($obdo) .
+ pack("p LL LL", $buf, $start, $count);
+
+ my $rc = ioctl(DEV_OBD, &OBD_IOC_PUNCH, $packed);
+
+ $retval = unpack("l", $packed);
+
+ if (!defined $rc) {
+ print STDERR "ioctl failed: $!\n";
+ } elsif ($rc eq "0 but true") {
+ if ($retval >= 0) {
+ print "\nPunched $retval of an attempted $count bytes.\n";
+ print "Finished (success)\n";
+ } else {
+ print "Finished (error $retval)\n";
+ }
+ } else {
+ print "ioctl returned error code $rc.\n";
+ }
+}
+