mirror of
https://github.com/TomHarte/CLK.git
synced 2024-11-29 12:50:28 +00:00
Started taking further steps towards CSW support; reading the ZLib documentation is next.
This commit is contained in:
parent
368bff1a82
commit
33eadb5549
@ -12,8 +12,68 @@ using namespace Storage::Tape;
|
|||||||
|
|
||||||
CSW::CSW(const char *file_name) :
|
CSW::CSW(const char *file_name) :
|
||||||
Storage::FileHolder(file_name) {
|
Storage::FileHolder(file_name) {
|
||||||
|
if(file_stats_.st_size < 0x20) throw ErrorNotCSW;
|
||||||
|
|
||||||
|
// Check signature.
|
||||||
|
char identifier[22];
|
||||||
|
char signature[] = "Compressed Square Wave";
|
||||||
|
fread(identifier, 1, 22, file_);
|
||||||
|
if(memcmp(identifier, signature, strlen(signature))) throw ErrorNotCSW;
|
||||||
|
|
||||||
|
// Check terminating byte.
|
||||||
|
if(fgetc(file_) != 0x1a) throw ErrorNotCSW;
|
||||||
|
|
||||||
|
// Get version file number.
|
||||||
|
uint8_t major_version = (uint8_t)fgetc(file_);
|
||||||
|
uint8_t minor_version = (uint8_t)fgetc(file_);
|
||||||
|
|
||||||
|
// Reject if this is an unknown version.
|
||||||
|
if(major_version > 2 || !major_version || minor_version > 1) throw ErrorNotCSW;
|
||||||
|
|
||||||
|
// The header now diverges based on version.
|
||||||
|
if(major_version == 1) {
|
||||||
|
pulse_.length.clock_rate = fgetc16le();
|
||||||
|
|
||||||
|
if(fgetc(file_) != 1) throw ErrorNotCSW;
|
||||||
|
compression_type_ = RLE;
|
||||||
|
|
||||||
|
pulse_.type = (fgetc(file_) & 1) ? Pulse::High : Pulse::Low;
|
||||||
|
|
||||||
|
fseek(file_, 0x20, SEEK_SET);
|
||||||
|
} else {
|
||||||
|
pulse_.length.clock_rate = fgetc32le();
|
||||||
|
number_of_waves_ = fgetc32le();
|
||||||
|
switch(fgetc(file_)) {
|
||||||
|
case 1: compression_type_ = RLE; break;
|
||||||
|
case 2: compression_type_ = ZRLE; break;
|
||||||
|
default: throw ErrorNotCSW;
|
||||||
|
}
|
||||||
|
|
||||||
|
pulse_.type = (fgetc(file_) & 1) ? Pulse::High : Pulse::Low;
|
||||||
|
uint8_t extension_length = (uint8_t)fgetc(file_);
|
||||||
|
|
||||||
|
if(file_stats_.st_size < 0x34 + extension_length) throw ErrorNotCSW;
|
||||||
|
fseek(file_, 0x34 + extension_length, SEEK_SET);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(compression_type_ == ZRLE) {
|
||||||
|
inflation_stream_.zalloc = Z_NULL;
|
||||||
|
inflation_stream_.zfree = Z_NULL;
|
||||||
|
inflation_stream_.opaque = Z_NULL;
|
||||||
|
inflation_stream_.avail_in = 0;
|
||||||
|
inflation_stream_.next_in = Z_NULL;
|
||||||
|
int result = inflateInit(&inflation_stream_);
|
||||||
|
if(result != Z_OK) throw ErrorNotCSW;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CSW::~CSW() {
|
||||||
|
if(compression_type_ == ZRLE) {
|
||||||
|
inflateEnd(&inflation_stream_);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
bool CSW::is_at_end() {
|
bool CSW::is_at_end() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -12,6 +12,8 @@
|
|||||||
#include "../Tape.hpp"
|
#include "../Tape.hpp"
|
||||||
#include "../../FileHolder.hpp"
|
#include "../../FileHolder.hpp"
|
||||||
|
|
||||||
|
#include <zlib.h>
|
||||||
|
|
||||||
namespace Storage {
|
namespace Storage {
|
||||||
namespace Tape {
|
namespace Tape {
|
||||||
|
|
||||||
@ -26,6 +28,7 @@ class CSW: public Tape, public Storage::FileHolder {
|
|||||||
@throws ErrorNotCSW if this file could not be opened and recognised as a valid CSW file.
|
@throws ErrorNotCSW if this file could not be opened and recognised as a valid CSW file.
|
||||||
*/
|
*/
|
||||||
CSW(const char *file_name);
|
CSW(const char *file_name);
|
||||||
|
~CSW();
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
ErrorNotCSW
|
ErrorNotCSW
|
||||||
@ -37,6 +40,14 @@ class CSW: public Tape, public Storage::FileHolder {
|
|||||||
private:
|
private:
|
||||||
void virtual_reset();
|
void virtual_reset();
|
||||||
Pulse virtual_get_next_pulse();
|
Pulse virtual_get_next_pulse();
|
||||||
|
|
||||||
|
Pulse pulse_;
|
||||||
|
enum CompressionType {
|
||||||
|
RLE,
|
||||||
|
ZRLE
|
||||||
|
} compression_type_;
|
||||||
|
uint32_t number_of_waves_;
|
||||||
|
z_stream inflation_stream_;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -58,6 +58,8 @@ class Tape {
|
|||||||
/// Advances or reverses the tape to the last time before or at @c time from which a pulse starts.
|
/// Advances or reverses the tape to the last time before or at @c time from which a pulse starts.
|
||||||
virtual void seek(Time &time);
|
virtual void seek(Time &time);
|
||||||
|
|
||||||
|
virtual ~Tape() {};
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Time current_time_, next_time_;
|
Time current_time_, next_time_;
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user