--- a/RDI_PD0_IO.pl
+++ b/RDI_PD0_IO.pl
@@ -1,13 +1,13 @@
#======================================================================
-# / D A T A / S R C / O C E A N O G R A P H Y / A D C P _ T O O L S / R D I _ B B _ R E A D . P L
+# R D I _ P D 0 _ I O . P L
# doc: Sat Jan 18 14:54:43 2003
-# dlm: Thu Feb 27 10:28:29 2020
+# dlm: Sun Apr 12 20:02:30 2020
# (c) 2003 A.M. Thurnherr
-# uE-Info: 716 1 NIL 0 0 72 0 2 4 NIL ofnI
+# uE-Info: 123 72 NIL 0 0 72 0 2 4 NIL ofnI
#======================================================================
-
+
# Read RDI PD0 binary data files (*.[0-9][0-9][0-9])
-
+
# HISTORY:
# Jan 18, 2003: - incepted aboard the Aurora Australis (KAOS)
# Jan 19, 2003: - continued
@@ -117,8 +117,12 @@
# - removed old BT_PRESENT code
# Jun 28, 2019: - renamed SECONDS to SECOND for consistency
# Jun 30, 2019: - added dirty flag to prevent bad PD0 patching
-# Feb 13, 2020: - added support for $readDataProgress
+# - added $show_progress
+# Feb 13, 2020: - added support for $readDataProgress (to Jun 13 version)
+# Apr 12, 2020: - merged laptop and whoosher versions which both implemented
+# progreass; not sure whether this merge is successful
+
# FIRMWARE VERSIONS:
# It appears that different firmware versions generate different file
# structures. Currently (Sep 2005) these routines have been tested
@@ -130,7 +134,7 @@
# 16.12 WH300 (1) FSU A0304 53
# 16.21 WH300 (1) LDEO NBP0402 53
# 16.27 WH300 (2) Nash ? 59
-
+
# PD0 FILE FORMAT EXTENSIONS:
#
# - file creator encoded in DATA_SOURCE_ID
@@ -148,7 +152,7 @@
# - HEADING can be missing (0xF000 badval, as 0x8000 is valid 327.68 heading)
#
# - DATA_SOURCE_ID = 0xE0 produced by editPD0
-
+
# NOTES:
# - RDI stores data in VAX/Intel byte order (little endian)
# - the output data structure does not exactly mirror the file data
@@ -180,7 +184,7 @@
# - defining the variable "$RDI_PD0_IO::IGNORE_Y2K_CLOCK" before calling &readData()
# makes the code ignore the Y2K clock and use the old clock instead; this
# is used for Dan Torres' KVH system
-
+
# &readData() returns perl obj (ref to anonymous hash) with the following
# structure:
#
@@ -315,70 +319,72 @@
# BT_SIGNAL_STRENGTH[beam] scalars 0--255
# HIGH_GAIN bool 1, undefined
# LOW_GAIN bool 1, undefined
-
- use strict;
- use Time::Local; # timegm()
-
+
+use strict;
+use Time::Local; # timegm()
+
+$RDI_PD0_IO::show_progress = 0; # when set, print . every 1000 ens read
+
#----------------------------------------------------------------------
# Time Conversion Subroutines
# - prepended with _ to avoid conflicts with [libconv.pl]
#----------------------------------------------------------------------
-
- sub _monthLength($$) # of days in month
- {
- my($Y,$M) = @_;
-
- return 31 if ($M==1 || $M==3 || $M==5 || $M==7 ||
- $M==8 || $M==10 || $M==12);
- return 30 if ($M==4 || $M==6 || $M==9 || $M==11);
- return 28 if ($Y%4 != 0);
- return 29 if ($Y%100 != 0);
- return 28 if ($Y%400 > 0);
- return 29;
- }
-
- { my($epoch,$lM,$lD,$lY,$ldn); # static scope
-
- sub _dayNo($$$$$$)
- {
- my($Y,$M,$D,$h,$m,$s) = @_;
- my($dn);
-
- if ($Y==$lY && $M==$lM && $D==$lD) { # same day as last samp
- $dn = $ldn;
- } else { # new day
- $epoch = $Y unless defined($epoch); # 1st call
- $lY = $Y; $lM = $M; $lD = $D; # store
-
- for ($dn=0,my($cY)=$epoch; $cY<$Y; $cY++) { # multiple years
- $dn += 337 + &_monthLength($Y,$M);
- }
-
- $dn += $D; # day in month
- while (--$M > 0) { # preceding months
- $dn += &_monthLength($Y,$M);
- }
-
- $ldn = $dn; # store
+
+sub _monthLength($$) # of days in month
+{
+ my($Y,$M) = @_;
+
+ return 31 if ($M==1 || $M==3 || $M==5 || $M==7 ||
+ $M==8 || $M==10 || $M==12);
+ return 30 if ($M==4 || $M==6 || $M==9 || $M==11);
+ return 28 if ($Y%4 != 0);
+ return 29 if ($Y%100 != 0);
+ return 28 if ($Y%400 > 0);
+ return 29;
+}
+
+{ my($epoch,$lM,$lD,$lY,$ldn); # static scope
+
+ sub _dayNo($$$$$$)
+ {
+ my($Y,$M,$D,$h,$m,$s) = @_;
+ my($dn);
+
+ if ($Y==$lY && $M==$lM && $D==$lD) { # same day as last samp
+ $dn = $ldn;
+ } else { # new day
+ $epoch = $Y unless defined($epoch); # 1st call
+ $lY = $Y; $lM = $M; $lD = $D; # store
+
+ for ($dn=0,my($cY)=$epoch; $cY<$Y; $cY++) { # multiple years
+ $dn += 337 + &_monthLength($Y,$M);
}
- return $dn + $h/24 + $m/24/60 + $s/24/3600;
+
+ $dn += $D; # day in month
+ while (--$M > 0) { # preceding months
+ $dn += &_monthLength($Y,$M);
+ }
+
+ $ldn = $dn; # store
}
-
- } # static scope
-
+ return $dn + $h/24 + $m/24/60 + $s/24/3600;
+ }
+
+} # static scope
+
#----------------------------------------------------------------------
# Read Data
#----------------------------------------------------------------------
-
- my($WBRcfn,$WBPcfn); # current file names for reading/patching
- my($BIT_errors) = 0; # built-in-test errors
-
- my($FmtErr) = "%s: illegal %s Id 0x%04x at ensemble %d";
-
+
+my($WBRcfn,$WBPcfn); # current file names for reading/patching
+my($BIT_errors) = 0; # built-in-test errors
+
+my($FmtErr) = "%s: illegal %s Id 0x%04x at ensemble %d";
+
#----------------------------------------------------------------------
# skip to next valid start of ensemble (skip over garbage)
#----------------------------------------------------------------------
-
+
sub goto_next_ens(@)
{
my($fh,$return_skipped) = @_; # if return_skipped not set, return file pos
@@ -392,7 +398,7 @@
if ($dta == 0x7f) {
$found++;
} elsif ($found==1 &&
- ($dta==0xE0 || # from editPD0
+ ($dta==0xE0 || # from editPD0
(($dta&0xF0)==0xA0 && ($dta&0x0F)<8))) { # from IMP+LADCP or KVH+LADCP
$found++;
} elsif ($found == 0) {
@@ -406,7 +412,7 @@
}
my($fpos) = ($found < 2) ? undef : sysseek($fh,-2,1);
return $skipped if ($return_skipped);
-
+
if ($skipped) {
if (eof($fh)) {
# 04/18/18: disabled the following line of code because it is very common at
@@ -419,16 +425,16 @@
print(STDERR "WARNING (RDI_PD0_IO): $skipped garbage bytes in PD0 file beginning at byte $garbage_start\n");
}
}
-
+
return $fpos;
}
-
+
#----------------------------------------------------------------------
# readHeader(file_name,^dta) WBRhdr(^data)
# - read header data
# - also includes some data from 1st ens
#----------------------------------------------------------------------
-
+
sub readHeader(@)
{
my($fn,$dta,$suppress_error) = @_;
@@ -436,11 +442,11 @@
open(WBRF,$WBRcfn) || die("$WBRcfn: $!");
if (WBRhdr($dta)) {
return 1;
- } elsif ($suppress_error) {
+ } elsif ($suppress_error) {
return undef;
- } else {
+ } else {
die("$WBRcfn: Insufficient data\n");
- }
+ }
}
sub WBRhdr($)
@@ -505,9 +511,9 @@
$dta->{INSTRUMENT_TYPE} = 'Explorer';
} elsif ($dta->{FIXED_LEADER_BYTES} == 60) { # OS75
$dta->{INSTRUMENT_TYPE} = 'Ocean Surveyor';
- } else {
+ } else {
$dta->{INSTRUMENT_TYPE} = 'unknown';
- }
+ }
#--------------------------------
# Variable Leader: SPEED_OF_SOUND
@@ -518,13 +524,13 @@
$id = unpack('v',$buf);
if ($dta->{INSTRUMENT_TYPE} eq 'Ocean Surveyor') {
$id == 0x0081 || printf(STDERR $FmtErr."\n",$WBRcfn,"Variable Leader",$id,1);
- } else {
+ } else {
$id == 0x0080 || printf(STDERR $FmtErr."\n",$WBRcfn,"Variable Leader",$id,1);
- }
+ }
sysseek(WBRF,12,1) || die("$WBRcfn: $!"); # skip up to speed of sound
sysread(WBRF,$buf,2) == 2 || die("$WBRcfn: $!");
$dta->{SPEED_OF_SOUND} = unpack('v',$buf);
-
+
#--------------------
# FIXED LEADER
#--------------------
@@ -546,36 +552,36 @@
if ($dta->{INSTRUMENT_TYPE} eq 'Ocean Surveyor') {
$id == 0x0001 || printf(STDERR $FmtErr."\n",$WBRcfn,"Fixed Leader",$id,0);
- } else {
+ } else {
$id == 0x0000 || printf(STDERR $FmtErr."\n",$WBRcfn,"Fixed Leader",$id,0);
- }
+ }
-# $dta->{BEAM_FREQUENCY} = 2**($B1 & 0x07) * 75; # nominal
- if (($B1&0x07) == 0b000) { $dta->{BEAM_FREQUENCY} = 76.8; } # actual
- elsif (($B1&0x07) == 0b001) { $dta->{BEAM_FREQUENCY} = 153.6; }
- elsif (($B1&0x07) == 0b010) { $dta->{BEAM_FREQUENCY} = 307.2; }
- elsif (($B1&0x07) == 0b011) { $dta->{BEAM_FREQUENCY} = 614.4; }
+# $dta->{BEAM_FREQUENCY} = 2**($B1 & 0x07) * 75; # nominal
+ if (($B1&0x07) == 0b000) { $dta->{BEAM_FREQUENCY} = 76.8; } # actual
+ elsif (($B1&0x07) == 0b001) { $dta->{BEAM_FREQUENCY} = 153.6; }
+ elsif (($B1&0x07) == 0b010) { $dta->{BEAM_FREQUENCY} = 307.2; }
+ elsif (($B1&0x07) == 0b011) { $dta->{BEAM_FREQUENCY} = 614.4; }
elsif (($B1&0x07) == 0b100) { $dta->{BEAM_FREQUENCY} = 1228.8; }
elsif (($B1&0x07) == 0b101) { $dta->{BEAM_FREQUENCY} = 2457.6; }
else { die(sprintf("$WBRcfn: cannot decode BEAM_FREQUENCY (%03b)\n",$B1&0x07)); }
- $dta->{CONVEX_BEAM_PATTERN} = 1 if ($B1 & 0x08);
- $dta->{CONCAVE_BEAM_PATTERN} = 1 if (!($B1 & 0x08));
- $dta->{SENSOR_CONFIG} = ($B1 & 0x30) >> 4;
- $dta->{XDUCER_HEAD_ATTACHED} = 1 if ($B1 & 0x40);
+ $dta->{CONVEX_BEAM_PATTERN} = 1 if ($B1 & 0x08);
+ $dta->{CONCAVE_BEAM_PATTERN} = 1 if (!($B1 & 0x08));
+ $dta->{SENSOR_CONFIG} = ($B1 & 0x30) >> 4;
+ $dta->{XDUCER_HEAD_ATTACHED} = 1 if ($B1 & 0x40);
if (($B2 & 0x03) == 0x00) { $dta->{BEAM_ANGLE} = 15; }
elsif (($B2 & 0x03) == 0x01) { $dta->{BEAM_ANGLE} = 20; }
elsif (($B2 & 0x03) == 0x02) { $dta->{BEAM_ANGLE} = 30; }
if (($B2 & 0xF0) == 0x40) { $dta->{N_BEAMS} = 4; }
elsif (($B2 & 0xF0) == 0x50) { $dta->{N_BEAMS} = 5; $dta->{N_DEMODS} = 3; }
- elsif (($B2 & 0xF0) == 0xF0) { $dta->{N_BEAMS} = 5; $dta->{N_DEMODS} = 2; }
+ elsif (($B2 & 0xF0) == 0xF0) { $dta->{N_BEAMS} = 5; $dta->{N_DEMODS} = 2; }
- $dta->{BIN_LENGTH} /= 100;
- $dta->{BLANKING_DISTANCE} /= 100;
+ $dta->{BIN_LENGTH} /= 100;
+ $dta->{BLANKING_DISTANCE} /= 100;
- $dta->{MAX_ERROR_VELOCITY} /= 1000;
- $dta->{TIME_BETWEEN_PINGS} *= 60;
+ $dta->{MAX_ERROR_VELOCITY} /= 1000;
+ $dta->{TIME_BETWEEN_PINGS} *= 60;
$dta->{TIME_BETWEEN_PINGS} += $B3 + $B4/100;
$dta->{BEAM_COORDINATES} = 1 if (($B5 & 0x18) == 0x00);
@@ -584,8 +590,8 @@
$dta->{EARTH_COORDINATES} = 1 if (($B5 & 0x18) == 0x18);
$dta->{PITCH_AND_ROLL_USED} = 1 if ($B5 & 0x04);
$dta->{USE_3_BEAM_ON_LOW_CORR} = 1 if ($B5 & 0x02);
- $dta->{BIN_MAPPING_ALLOWED} = 1 if ($B5 & 0x01);
-
+ $dta->{BIN_MAPPING_ALLOWED} = 1 if ($B5 & 0x01);
+
$dta->{HEADING_ALIGNMENT} =
($dta->{EARTH_COORDINATES} || $dta->{SHIP_COORDINATES}) ?
$dta->{HEADING_ALIGNMENT} / 100 : undef;
@@ -599,7 +605,7 @@
$dta->{USE_PITCH_SENSOR} = 1 if ($B6 & 0x08);
$dta->{USE_ROLL_SENSOR} = 1 if ($B6 & 0x04);
$dta->{USE_CONDUCTIVITY_SENSOR} = 1 if ($B6 & 0x02);
- $dta->{USE_TEMPERATURE_SENSOR} = 1 if ($B6 & 0x01);
+ $dta->{USE_TEMPERATURE_SENSOR} = 1 if ($B6 & 0x01);
$dta->{SPEED_OF_SOUND_CALCULATED} = 1 if ($B7 & 0x40);
$dta->{PRESSURE_SENSOR_AVAILABLE} = 1 if ($B7 & 0x20);
@@ -607,14 +613,14 @@
$dta->{PITCH_SENSOR_AVAILABLE} = 1 if ($B7 & 0x08);
$dta->{ROLL_SENSOR_AVAILABLE} = 1 if ($B7 & 0x04);
$dta->{CONDUCTIVITY_SENSOR_AVAILABLE} = 1 if ($B7 & 0x02);
- $dta->{TEMPERATURE_SENSOR_AVAILABLE} = 1 if ($B7 & 0x01);
+ $dta->{TEMPERATURE_SENSOR_AVAILABLE} = 1 if ($B7 & 0x01);
- $dta->{DISTANCE_TO_BIN1_CENTER} /= 100;
- $dta->{TRANSMITTED_PULSE_LENGTH} /= 100;
+ $dta->{DISTANCE_TO_BIN1_CENTER} /= 100;
+ $dta->{TRANSMITTED_PULSE_LENGTH} /= 100;
- $dta->{FALSE_TARGET_THRESHOLD} = undef
+ $dta->{FALSE_TARGET_THRESHOLD} = undef
if ($dta->{FALSE_TARGET_THRESHOLD} == 255);
- $dta->{TRANSMIT_LAG_DISTANCE} /= 100;
+ $dta->{TRANSMIT_LAG_DISTANCE} /= 100;
if ($dta->{INSTRUMENT_TYPE} eq 'Workhorse') {
sysread(WBRF,$buf,11) == 11 || die("$WBRcfn: $!");
@@ -622,17 +628,17 @@
unpack('vvvvvC',$buf);
$dta->{CPU_SERIAL_NUMBER} = sprintf("%04X%04X%04X%04X",$W1,$W2,$W3,$W4);
-
+
$dta->{NARROW_BANDWIDTH} = ($W5 == 1);
$dta->{WIDE_BANDWIDTH} = ($W5 == 0);
- $dta->{TRANSMIT_POWER_HIGH} = ($dta->{TRANSMIT_POWER} == 255);
+ $dta->{TRANSMIT_POWER_HIGH} = ($dta->{TRANSMIT_POWER} == 255);
- if ($dta->{FIXED_LEADER_BYTES} == 59) { # new style with serial number
+ if ($dta->{FIXED_LEADER_BYTES} == 59) { # new style with serial number
sysread(WBRF,$buf,6) == 6 || die("$WBRcfn: $!");
- ($dummy,$dta->{SERIAL_NUMBER},$dummy) = # last bytes is beam angle, but that info has
- unpack('CVC',$buf); # already been provided above
+ ($dummy,$dta->{SERIAL_NUMBER},$dummy) = # last bytes is beam angle, but that info has
+ unpack('CVC',$buf); # already been provided above
}
- }
+ }
if ($dta->{INSTRUMENT_TYPE} eq 'Explorer') {
sysread(WBRF,$buf,16) == 16 || die("$WBRcfn: $!");
@@ -640,13 +646,13 @@
unpack('VVvvV',$buf);
$dta->{NARROW_BANDWIDTH} = ($W5 == 1);
$dta->{WIDE_BANDWIDTH} = ($W5 == 0);
- }
+ }
#-----------------------
# 1st ENSEMBLE, BT Setup
#-----------------------
-# CODE DISABLED BECAUSE BT_PRESENT FLAG WAS REMOVED. WITHOUT THIS CODE,
+# CODE DISABLED BECAUSE BT_PRESENT FLAG WAS REMOVED. WITHOUT THIS CODE,
# [listHdr] DOES NOT LIST ANY BT INFO
#
# if ($dta->{BT_PRESENT}) {
@@ -659,44 +665,43 @@
#
# $id == 0x0600 ||
# printf(STDERR $FmtErr."\n",$WBRcfn,"Bottom Track",$id,0,tell(WBRF));
-#
+#
# $dta->{BT_MAX_ERROR_VELOCITY} =
# $dta->{BT_MAX_ERROR_VELOCITY} ? $dta->{BT_MAX_ERROR_VELOCITY} / 1000
# : undef;
-#
+#
# sysseek(WBRF,28,1) || die("$WBRcfn: $!");
# sysread(WBRF,$buf,6) == 6 || die("$WBRcfn: $!");
# ($dta->{BT_RL_MIN_SIZE},$dta->{BT_RL_NEAR},$dta->{BT_RL_FAR})
# = unpack('vvv',$buf);
-#
+#
# $dta->{BT_RL_MIN_SIZE} /= 10;
# $dta->{BT_RL_NEAR} /= 10;
# $dta->{BT_RL_FAR} /= 10;
#
# sysseek(WBRF,20,1) || die("$WBRcfn: $!"); # skip data
# sysread(WBRF,$buf,2) == 2 || die("$WBRcfn: $!");
-# $dta->{BT_MAX_TRACKING_DEPTH} = unpack('v',$buf) / 10;
-# }
+# $dta->{BT_MAX_TRACKING_DEPTH} = unpack('v',$buf) / 10;
+# }
- return $dta;
+ return $dta;
}
#----------------------------------------------------------------------
# readData(file_name,^data[,first_ens,last_ens[,last_bin]])
-# - read ensembles
+# - read ensembles
# - read all ensembles unless first_ens and last_ens are given
# - read all bins unless last_bin is given
-# - if global var $readDataProgress > 0, a . is printed
-# every $readaDataProgress ensembles
+# - NB: CODE GETS PROGRESSIVELY SLOWER => HUGE PAIN FOR LARGE FILES
#----------------------------------------------------------------------
sub readData(@)
{
my($fn,$dta,$fe,$le,$lb) = @_;
$WBRcfn = $fn;
- open(WBRF,$WBRcfn) || die("$WBRcfn: $!\n");
- WBRhdr($dta) || die("$WBRcfn: Insufficient Data\n");
- $lb = $dta->{N_BINS}
+ open(WBRF,$WBRcfn) || die("$WBRcfn: $!\n");
+ WBRhdr($dta) || die("$WBRcfn: Insufficient Data\n");
+ $lb = $dta->{N_BINS}
unless (numberp($lb) && $lb>=1 && $lb<=$dta->{N_BINS});
WBRens($lb,$dta->{FIXED_LEADER_BYTES},\@{$dta->{ENSEMBLE}},$fe,$le);
print(STDERR "$WBRcfn: $BIT_errors built-in-test errors\n")
@@ -710,11 +715,10 @@
my($ens,$ensNo,$dayStart,$ens_length,$hid,$did,$el);
local our($ndt,$buf,$id,$start_ens,@WBRofs);
- sysseek(WBRF,0,0) || die("$WBRcfn: $!");
+ sysseek(WBRF,0,0) || die("$WBRcfn: $!");
ENSEMBLE:
for ($ens=0; 1; $ens++) {
-# die unless defined($global::readDataProgress);
- print(STDERR '.') if ($global::readDataProgress>0 && ($ens%$global::readDataProgress)==0);
+ print(STDERR '.') if ($RDI_PD0_IO::show_progress && $ens % 1000 == 0);
$start_ens = goto_next_ens(\*WBRF);
last unless defined($start_ens);
@@ -748,7 +752,7 @@
${$E}[$ens]->{PRODUCER} = 'editPD0 (Thurnherr software)';
} else {
${$E}[$ens]->{PRODUCER} = 'unknown';
- }
+ }
if (defined($ens_length) && ($el != $ens_length)) {
$RDI_PD0_IO::File_Dirty = 1;
@@ -757,7 +761,7 @@
$ens--;
next;
}
-
+
$ens_length = $el;
## printf(STDERR "$WBRcfn: WARNING: unexpected number of data types (%d, ens=$ens)\n",$ndt),last
@@ -773,7 +777,7 @@
@WBRofs = unpack("v$ndt",$buf);
$fixed_leader_bytes = $WBRofs[1] - $WBRofs[0];
# print(STDERR "@WBRofs\n");
-
+
#-------------------------------
# Make Sure Ensemble is Complete
#-------------------------------
@@ -794,12 +798,12 @@
# print(STDERR "BAD CHECKSUM\n");
pop(@{$E}); $ens--;
next;
- }
+ }
#------------------------------
# Variable Leader
#------------------------------
-
+
my($lastEns) = $ensNo;
sysseek(WBRF,$start_ens+$WBRofs[1],0) || die("$WBRcfn: $!");
sysread(WBRF,$buf,4) == 4 || die("$WBRcfn: $!");
@@ -808,10 +812,10 @@
if (${$E}[$ens]->{INSTRUMENT_TYPE} eq 'Ocean Surveyor') {
$id == 0x0081 ||
die(sprintf($FmtErr,$WBRcfn,"Variable Leader",$id,$ensNo + ($lastEns - ($lastEns & 0xFFFF))));
- } else {
+ } else {
$id == 0x0080 ||
die(sprintf($FmtErr,$WBRcfn,"Variable Leader",$id,$ensNo + ($lastEns - ($lastEns & 0xFFFF))));
- }
+ }
# if ($fixed_leader_bytes==42 || $fixed_leader_bytes==58) { # BB150 & Explorer DVL (if DISABLED!)
sysread(WBRF,$buf,7) == 7 || die("$WBRcfn: $!"); # always read pre-Y2K clock
@@ -836,9 +840,9 @@
next ENSEMBLE;
}
}
-
+
${$E}[$ens]->{NUMBER} = $ensNo;
-
+
sysread(WBRF,$buf,30) == 30 || die("$WBRcfn: $!");
(${$E}[$ens]->{BUILT_IN_TEST_ERROR},${$E}[$ens]->{SPEED_OF_SOUND},
${$E}[$ens]->{XDUCER_DEPTH},${$E}[$ens]->{HEADING},
@@ -862,7 +866,7 @@
#-------------------------------------------------
# IMP EXTENSION: PITCH/ROLL/HEADING CAN BE MISSING
#-------------------------------------------------
-
+
${$E}[$ens]->{HEADING} = (${$E}[$ens]->{HEADING} == 0xF000)
? undef
: ${$E}[$ens]->{HEADING} / 100;
@@ -870,9 +874,9 @@
? undef
: unpack('s',pack('S',${$E}[$ens]->{PITCH})) / 100;
${$E}[$ens]->{ROLL} = (${$E}[$ens]->{ROLL} == 0x8000)
- ? undef
- : unpack('s',pack('S',${$E}[$ens]->{ROLL})) / 100;
-
+ ? undef
+ : unpack('s',pack('S',${$E}[$ens]->{ROLL})) / 100;
+
${$E}[$ens]->{TEMPERATURE} = unpack('s',pack('S',${$E}[$ens]->{TEMPERATURE})) / 100;
${$E}[$ens]->{MIN_PRE_PING_WAIT_TIME} *= 60;
${$E}[$ens]->{MIN_PRE_PING_WAIT_TIME} += $B1 + $B2/100;
@@ -883,7 +887,7 @@
!defined($RDI_PD0_IO::IGNORE_Y2K_CLOCK)) {
sysread(WBRF,$buf,23) == 23 || die("$WBRcfn: $!");
(${$E}[$ens]->{ERROR_STATUS_WORD},
- $dummy,${$E}[$ens]->{PRESSURE},${$E}[$ens]->{PRESSURE_STDDEV},
+ $dummy,${$E}[$ens]->{PRESSURE},${$E}[$ens]->{PRESSURE_STDDEV},
$dummy,${$E}[$ens]->{YEAR},$B3,${$E}[$ens]->{MONTH},
${$E}[$ens]->{DAY},${$E}[$ens]->{HOUR},${$E}[$ens]->{MINUTE},
${$E}[$ens]->{SECOND},$B4)
@@ -895,7 +899,7 @@
${$E}[$ens]->{SECOND} += $B4/100;
}
-# THE FOLLOWING LINE OF CODE WAS REMOVED 7/30/2016 WHEN I ADDED A POP
+# THE FOLLOWING LINE OF CODE WAS REMOVED 7/30/2016 WHEN I ADDED A POP
# TO THE last STATEMENT ABOVE (INCOMPLETE ENSEMBLE)
# THE LINE WAS RE-ENABLED ON 12/23/2017 BECAUSE OTHERWISE THE
# ANSLOPE II PROFILES IN THE HOWTO CANNOT BE READ.
@@ -904,12 +908,12 @@
if ($fixed_leader_bytes == 58) { # Explorer DVL
sysread(WBRF,$buf,14) == 14 || die("$WBRcfn: $!");
(${$E}[$ens]->{ERROR_STATUS_WORD},
- $dummy,${$E}[$ens]->{PRESSURE},${$E}[$ens]->{PRESSURE_STDDEV})
+ $dummy,${$E}[$ens]->{PRESSURE},${$E}[$ens]->{PRESSURE_STDDEV})
= unpack('VvVV',$buf);
${$E}[$ens]->{PRESSURE} /= 1000;
${$E}[$ens]->{PRESSURE_STDDEV} /= 1000;
}
-
+
${$E}[$ens]->{DATE}
= sprintf("%02d/%02d/%d",${$E}[$ens]->{MONTH},
${$E}[$ens]->{DAY},
@@ -928,7 +932,7 @@
if (${$E}[$ens]->{MONTH} == 0) { # no time info
${$E}[$ens]->{UNIX_TIME} = 0;
${$E}[$ens]->{SECNO} = 0;
- } else {
+ } else {
# print(STDERR "[$ens]->${$E}[$ens]->{MINUTE}:${$E}[$ens]->{HOUR},${$E}[$ens]->{DAY},${$E}[$ens]->{MONTH},${$E}[$ens]->{YEAR}-<\n");
${$E}[$ens]->{UNIX_TIME}
= timegm(0,${$E}[$ens]->{MINUTE},
@@ -942,16 +946,16 @@
${$E}[$ens]->{MONTH}-1,
${$E}[$ens]->{YEAR})
unless defined($dayStart);
- ${$E}[$ens]->{SECNO} = ${$E}[$ens]->{UNIX_TIME} - $dayStart;
- }
+ ${$E}[$ens]->{SECNO} = ${$E}[$ens]->{UNIX_TIME} - $dayStart;
+ }
- sysseek(WBRF,$start_ens+$WBRofs[0]+4,0) # System Config / Fixed Leader
+ sysseek(WBRF,$start_ens+$WBRofs[0]+4,0) # System Config / Fixed Leader
|| die("$WBRcfn: $!");
sysread(WBRF,$buf,5) == 5 || die("$WBRcfn: $!");
($B1,$dummy,$dummy,$dummy,${$E}[$ens]->{N_BEAMS_USED})
- = unpack('CCCCC',$buf);
- ${$E}[$ens]->{XDUCER_FACING_UP} = 1 if ($B1 & 0x80);
+ = unpack('CCCCC',$buf);
+ ${$E}[$ens]->{XDUCER_FACING_UP} = 1 if ($B1 & 0x80);
${$E}[$ens]->{XDUCER_FACING_DOWN} = 1 unless ($B1 & 0x80);
#--------------------
@@ -963,7 +967,7 @@
my($vel_di) = WBRdtaIndex(0x0100);
die("no velocity data in ensemble #$ensNo\n")
unless defined($vel_di);
-
+
sysseek(WBRF,$start_ens+$WBRofs[$vel_di],0) || die("$WBRcfn: $!");
sysread(WBRF,$buf,2+$ndata*2) == 2+$ndata*2 || die("$WBRcfn: $!");
($id,@dta) = unpack("vv$ndata",$buf);
@@ -983,7 +987,7 @@
my($corr_di) = WBRdtaIndex(0x0200);
die("no correlation data in ensemble #$ensNo\n")
unless defined($corr_di);
-
+
sysseek(WBRF,$start_ens+$WBRofs[$corr_di],0) || die("$WBRcfn: $!");
sysread(WBRF,$buf,2+$ndata) == 2+$ndata || die("$WBRcfn: $!");
($id,@dta) = unpack("vC$ndata",$buf);
@@ -1002,7 +1006,7 @@
my($echo_di) = WBRdtaIndex(0x0300);
die("no echo intensity data in ensemble #$ensNo\n")
unless defined($echo_di);
-
+
sysseek(WBRF,$start_ens+$WBRofs[$echo_di],0) || die("$WBRcfn: $!");
sysread(WBRF,$buf,2+$ndata) == 2+$ndata || die("$WBRcfn: $!");
($id,@dta) = unpack("vC$ndata",$buf);
@@ -1023,7 +1027,7 @@
my($pctg_di) = WBRdtaIndex(0x0400);
die("no percent good data in ensemble #$ensNo\n")
unless defined($pctg_di);
-
+
sysseek(WBRF,$start_ens+$WBRofs[$pctg_di],0) || die("$WBRcfn: $!");
sysread(WBRF,$buf,2+$ndata) == 2+$ndata || die("$WBRcfn: $!");
($id,@dta) = unpack("vC$ndata",$buf);
@@ -1046,7 +1050,7 @@
unless (defined($pctg_di)) { # no BT found => next ens
sysseek(WBRF,$start_ens+$ens_length+2,0) || die("$WBRcfn: $!");
next;
- }
+ }
sysseek(WBRF,14,1) || die("$WBRcfn: $!"); # BT range, velocity, corr, %-good, ...
sysread(WBRF,$buf,28) == 28 || die("$WBRcfn: $!");
@@ -1072,7 +1076,10 @@
}
sysseek(WBRF,6,1) || die("$WBRcfn: $!"); # BT ref level stuff
- sysread(WBRF,$buf,20) == 20 || die("$WBRcfn: $!");
+ if (sysread(WBRF,$buf,20) != 20) { # EN642/PITA1
+ pop(@{$E});
+ last;
+ }
@dta = unpack('v4C4C4C4',$buf);
for ($beam=0; $beam<4; $beam++) {
${$E}[$ens]->{BT_RL_VELOCITY}[$beam] =
@@ -1107,8 +1114,8 @@
}
sysseek(WBRF,$start_ens+$ens_length+2,0) || die("$WBRcfn: $!");
} # ens loop
+ print(STDERR "\n") if ($RDI_PD0_IO::show_progress);
}
-print(STDERR "\n") if ($global::readDataProgress > 0);
sub WBRdtaIndex($)
{