Commit 399b7dcb authored by Sven Robertz's avatar Sven Robertz
Browse files

packed lengths and numbers seem to work in C and Java

parent e2b094d5
......@@ -496,7 +496,8 @@ aspect C_Decoder {
}
public void VariableSize.C_emitDecoderDecodeLimit(C_env env, int i) {
env.println(env.qualid + ".n_" + i + " = labcomm_decode_int(d);");
//env.println(env.qualid + ".n_" + i + " = labcomm_decode_int(d);");
env.println(env.qualid + ".n_" + i + " = labcomm_decode_packed32(d);");
}
public void ArrayType.C_emitDecoderDecodeLimit(C_env env) {
......@@ -721,7 +722,8 @@ aspect C_Encoder {
}
public void VariableSize.C_emitEncoderEncodeLimit(C_env env, int i) {
env.println("labcomm_encode_int(e, " + env.qualid + ".n_" + i + ");");
//env.println("labcomm_encode_int(e, " + env.qualid + ".n_" + i + ");");
env.println("labcomm_encode_packed32(e, " + env.qualid + ".n_" + i + ");");
}
public void ArrayType.C_emitEncoderEncodeLimit(C_env env) {
......
......@@ -38,11 +38,27 @@ aspect Signature {
}
public void addInt(int value, String comment) {
byte[] data = new byte[4];
for (int i = 0 ; i < 4 ; i++) {
data[3 - i] = (byte)((value >> (8 * i)) & 0xff);
}
add(data, comment);
byte[] packed = new byte[5];
// System.out.println("addInt: "+value);
int tmp = value;
int len = 0;
while( tmp >= 0x80 ) {
packed[len] = (byte) ((tmp & 0x7f) | 0x80 ) ;
tmp >>>= 7;
len++;
}
packed[len] = (byte) (tmp & 0x7f);
// System.out.println("packed: "+packed[len]+ "len = "+len);
add(java.util.Arrays.copyOf(packed, len+1), comment);
// byte[] data = new byte[4];
// for (int i = 0 ; i < 4 ; i++) {
// data[3 - i] = (byte)((value >> (8 * i)) & 0xff);
// }
// add(data, comment);
}
public void addString(String value, String comment) {
......@@ -196,4 +212,4 @@ aspect Signature {
return "_";
}
}
\ No newline at end of file
}
......@@ -12,6 +12,20 @@ static void handle_simple_IntString(simple_IntString *v,void *context) {
printf("Got IntString. x=%d, s=%s\n", v->x, v->s);
}
static void handle_simple_TwoArrays(simple_TwoArrays *d,void *context) {
printf("Got TwoArrays:");
int i;
for(i=0; i<2; i++) {
printf("%d ",d->fixed.a[i]);
}
printf("\n");
for(i=0; i<d->variable.n_1; i++) {
printf("%d ",d->variable.a[0+2*i]);
printf("%d ",d->variable.a[1+2*i]);
}
printf("\n");
}
int main(int argc, char *argv[]) {
int fd;
struct labcomm_decoder *decoder;
......@@ -29,6 +43,7 @@ int main(int argc, char *argv[]) {
labcomm_decoder_register_simple_TwoInts(decoder, handle_simple_TwoInts, context);
labcomm_decoder_register_simple_IntString(decoder, handle_simple_IntString, context);
labcomm_decoder_register_simple_TwoArrays(decoder, handle_simple_TwoArrays, context);
printf("Decoding:\n");
labcomm_decoder_run(decoder);
......
#include <stdio.h>
typedef unsigned int number;
unsigned char do_pack(unsigned char *buf, unsigned long i)
unsigned char do_pack(unsigned char *buf, number i)
{
printf("do_pack %lu == %lx\n", i, i);
unsigned long tmp = i;
number tmp = i;
unsigned char res = 0;
while ( tmp >= 0x80 ) {
......@@ -17,14 +18,16 @@ unsigned char do_pack(unsigned char *buf, unsigned long i)
return res+1;
}
unsigned long do_unpack(unsigned char *buf)
number do_unpack(unsigned char *buf)
{
unsigned long res=0;
number res=0;
unsigned char i=0;
unsigned char cont=1;
do {
res |= (buf[i] & 0x7f) << 7*i;
cont = buf[i++] & 0x80;
unsigned char c = buf[i];
res |= (c & 0x7f) << 7*i;
cont = c & 0x80;
i++;
} while(cont);
return res;
......@@ -65,7 +68,7 @@ int main()
print_packed(buf, len);
printf("... unpacks to %u\n\n", do_unpack(buf));
len = do_pack(buf, 0xffffffffffffffff);
len = do_pack(buf, 0xffffffff);
print_packed(buf, len);
printf("... unpacks to %lx\n", do_unpack(buf));
......
......@@ -108,7 +108,7 @@ static void do_encoder_register(struct labcomm_encoder *e,
context->sample = sample;
e->writer.write(&e->writer, labcomm_writer_start);
labcomm_encode_int(e, signature->type);
labcomm_encode_packed32(e, signature->type);
labcomm_encode_type_index(e, signature);
labcomm_encode_string(e, signature->name);
for (i = 0 ; i < signature->size ; i++) {
......@@ -204,7 +204,7 @@ void labcomm_encoder_free(labcomm_encoder_t* e)
void labcomm_encode_type_index(labcomm_encoder_t *e, labcomm_signature_t *s)
{
int index = get_encoder_index(e, s);
labcomm_encode_int(e, index);
labcomm_encode_packed32(e, index);
}
static int signature_writer(
......@@ -249,27 +249,32 @@ static void collect_flat_signature(
labcomm_decoder_t *decoder,
labcomm_encoder_t *signature_writer)
{
int type = labcomm_decode_int(decoder);
//int type = labcomm_decode_int(decoder);
int type = labcomm_decode_packed32(decoder);
// printf("%s: type=%x\n", __FUNCTION__, type);
if (type >= LABCOMM_USER) {
printf("Implement %s ...\n", __FUNCTION__);
printf("Implement %s ... (1) for type 0x%x\n", __FUNCTION__, type);
} else {
labcomm_encode_int(signature_writer, type);
//labcomm_encode_int(signature_writer, type);
labcomm_encode_packed32(signature_writer, type);
switch (type) {
case LABCOMM_ARRAY: {
int dimensions, i;
dimensions = labcomm_decode_int(decoder);
labcomm_encode_int(signature_writer, dimensions);
dimensions = labcomm_decode_packed32(decoder); //labcomm_decode_int(decoder); //unpack32
labcomm_encode_packed32(signature_writer, dimensions); //pack32
for (i = 0 ; i < dimensions ; i++) {
int n = labcomm_decode_int(decoder);
labcomm_encode_int(signature_writer, n);
int n = labcomm_decode_packed32(decoder); //labcomm_decode_int(decoder);
labcomm_encode_packed32(signature_writer, n); // labcomm_encode_int(signature_writer, n);
}
collect_flat_signature(decoder, signature_writer);
} break;
case LABCOMM_STRUCT: {
int fields, i;
fields = labcomm_decode_int(decoder);
labcomm_encode_int(signature_writer, fields);
//fields = labcomm_decode_int(decoder);
//labcomm_encode_int(signature_writer, fields);
fields = labcomm_decode_packed32(decoder);
labcomm_encode_packed32(signature_writer, fields);
for (i = 0 ; i < fields ; i++) {
char *name = labcomm_decode_string(decoder);
labcomm_encode_string(signature_writer, name);
......@@ -287,7 +292,7 @@ static void collect_flat_signature(
case LABCOMM_STRING: {
} break;
default: {
printf("Implement %s ...\n", __FUNCTION__);
printf("Implement %s (2) for type 0x%x...\n", __FUNCTION__, type);
} break;
}
}
......@@ -326,7 +331,9 @@ static int do_decode_one(labcomm_decoder_t *d)
if (result > 0) {
labcomm_decoder_context_t *context = d->context;
result = labcomm_decode_int(d);
// printf("do_decode_one: result = %x\n", result);
result = labcomm_decode_packed32(d);
// printf("do_decode_one: result(2) = %x\n", result);
if (result == LABCOMM_TYPEDEF || result == LABCOMM_SAMPLE) {
labcomm_encoder_t *e = labcomm_encoder_new(signature_writer, 0);
labcomm_signature_t signature;
......@@ -335,8 +342,9 @@ static int do_decode_one(labcomm_decoder_t *d)
e->writer.write(&e->writer, labcomm_writer_start);
signature.type = result;
index = labcomm_decode_int(d);
index = labcomm_decode_packed32(d); //int
signature.name = labcomm_decode_string(d);
// printf("do_decode_one: result = %x, index = %x, name=%s\n", result, index, signature.name);
collect_flat_signature(d, e);
signature.size = e->writer.pos;
signature.signature = e->writer.data;
......
......@@ -109,12 +109,45 @@ LABCOMM_DECODE(int, int)
LABCOMM_DECODE(long, long long)
LABCOMM_DECODE(float, float)
LABCOMM_DECODE(double, double)
static inline unsigned int labcomm_unpack32(labcomm_reader_t *r)
{
unsigned int res=0;
unsigned char i=0;
unsigned char cont=1;
do {
if (r->pos >= r->count) {
r->read(r, labcomm_reader_continue);
}
#ifdef IDIOTDEBUG
{
int k;
for(k=0; k<=r->pos; k++) printf("%2x\n", r->data[k]);
}
#endif
unsigned char c = r->data[r->pos];
res |= (c & 0x7f) << 7*i;
cont = c & 0x80;
#ifdef IDIOTDEBUG
printf("unpack32: %x (%x, %d, %d)\n", res, c, i, cont);
#endif
i++;
r->pos++;
} while(cont);
return res;
}
static inline unsigned int labcomm_decode_packed32(labcomm_decoder_t *d)
{
return labcomm_unpack32(&d->reader);
}
static inline char *labcomm_read_string(labcomm_reader_t *r)
{
char *result;
int length, i;
length = labcomm_read_int(r);
length = labcomm_unpack32(r);
result = malloc(length + 1);
for (i = 0 ; i < length ; i++) {
if (r->pos >= r->count) {
......@@ -235,12 +268,36 @@ LABCOMM_ENCODE(int, int)
LABCOMM_ENCODE(long, long long)
LABCOMM_ENCODE(float, float)
LABCOMM_ENCODE(double, double)
static inline void labcomm_pack32(labcomm_writer_t *w, unsigned int data)
{
unsigned int tmp, i;
tmp = data;
while (tmp >= 0x80) {
if (w->pos >= w->count) {
w->write(w, labcomm_writer_continue);
}
w->data[w->pos] = (tmp & 0x7f) | 0x80;
w->pos++;
tmp >>= 7;
}
w->data[w->pos] = tmp;
w->pos++;
}
static inline void labcomm_encode_packed32(labcomm_encoder_t *e, unsigned int data)
{
labcomm_pack32(&e->writer, data);
}
static inline void labcomm_write_string(labcomm_writer_t *w, char *s)
{
int length, i;
length = strlen((char*)s);
labcomm_write_int(w, length);
labcomm_pack32(w, length);
for (i = 0 ; i < length ; i++) {
if (w->pos >= w->count) {
w->write(w, labcomm_writer_continue);
......
......@@ -14,5 +14,6 @@ public interface LabCommDecoder {
public float decodeFloat() throws IOException;
public double decodeDouble() throws IOException;
public String decodeString() throws IOException;
public int decodePacked32() throws IOException;
}
\ No newline at end of file
}
......@@ -18,11 +18,11 @@ public class LabCommDecoderChannel implements LabCommDecoder {
public void runOne() throws Exception {
boolean done = false;
while (!done) {
int tag = decodeInt();
int tag = decodePacked32();
switch (tag) {
case LabComm.TYPEDEF:
case LabComm.SAMPLE: {
int index = decodeInt();
int index = decodePacked32();
String name = decodeString();
ByteArrayOutputStream signature = new ByteArrayOutputStream();
collectFlatSignature(new LabCommEncoderChannel(signature));
......@@ -55,20 +55,20 @@ public class LabCommDecoderChannel implements LabCommDecoder {
}
private void collectFlatSignature(LabCommEncoder out) throws IOException {
int type = decodeInt();
out.encodeInt(type);
int type = decodePacked32();
out.encodePacked32(type);
switch (type) {
case LabComm.ARRAY: {
int dimensions = decodeInt();
out.encodeInt(dimensions);
int dimensions = decodePacked32();
out.encodePacked32(dimensions);
for (int i = 0 ; i < dimensions ; i++) {
out.encodeInt(decodeInt());
out.encodePacked32(decodePacked32());
}
collectFlatSignature(out);
} break;
case LabComm.STRUCT: {
int fields = decodeInt();
out.encodeInt(fields);
int fields = decodePacked32();
out.encodePacked32(fields);
for (int i = 0 ; i < fields ; i++) {
out.encodeString(decodeString());
collectFlatSignature(out);
......@@ -124,9 +124,30 @@ public class LabCommDecoderChannel implements LabCommDecoder {
}
public String decodeString() throws IOException {
in.readShort(); // HACK
return in.readUTF();
//in.readShort(); // HACK
//return in.readUTF();
int len = decodePacked32() & 0xffffffff;
byte[] chars = new byte[len];
for(int i=0; i<len; i++) {
chars[i] = in.readByte();
}
return new String(chars);
}
public int decodePacked32() throws IOException {
long res=0;
byte i=0;
boolean cont=true;
do {
byte c = in.readByte();
res |= (c & 0x7f) << 7*i;
cont = (c & 0x80) != 0;
System.out.println("decodePacked32: "+res);
i++;
} while(cont);
return (int) (res & 0xffffffff);
}
}
......@@ -15,5 +15,6 @@ public interface LabCommEncoder {
public void encodeFloat(float value) throws IOException;
public void encodeDouble(double value) throws IOException;
public void encodeString(String value) throws IOException;
public void encodePacked32(long value) throws IOException;
}
\ No newline at end of file
}
......@@ -21,8 +21,8 @@ public class LabCommEncoderChannel implements LabCommEncoder {
public void register(LabCommDispatcher dispatcher) throws IOException {
int index = registry.add(dispatcher);
encodeInt(LabComm.SAMPLE);
encodeInt(index);
encodePacked32(LabComm.SAMPLE);
encodePacked32(index);
encodeString(dispatcher.getName());
byte[] signature = dispatcher.getSignature();
for (int i = 0 ; i < signature.length ; i++) {
......@@ -32,7 +32,7 @@ public class LabCommEncoderChannel implements LabCommEncoder {
}
public void begin(Class<? extends LabCommSample> c) throws IOException {
encodeInt(registry.getTag(c));
encodePacked32(registry.getTag(c));
}
public void end(Class<? extends LabCommSample> c) throws IOException {
......@@ -70,9 +70,31 @@ public class LabCommEncoderChannel implements LabCommEncoder {
}
public void encodeString(String value) throws IOException {
data.writeShort(0); // HACK...
data.writeUTF(value);
//data.writeShort(0); // HACK...
//data.writeUTF(value);
//kludge, to replace above hack with packed length
ByteArrayOutputStream tmpb = new ByteArrayOutputStream();
DataOutputStream tmps = new DataOutputStream(tmpb);
tmps.writeUTF(value);
tmps.flush();
byte[] tmp = tmpb.toByteArray();
encodePacked32(tmp.length-2);
for (int i = 2 ; i < tmp.length ; i++) {
encodeByte(tmp[i]);
}
}
public void encodePacked32(long value) throws IOException {
long tmp = value;
while( tmp >= 0x80 ) {
encodeByte( (byte) ((tmp & 0x7f) | 0x80 ) );
tmp >>>= 7;
}
encodeByte( (byte) (tmp & 0x7f) );
}
}
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment