#include "coolrt.h"
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
const char Object_string[] = "Object";
const char Int_string[] = "Int";
const char Bool_string[] = "Bool";
const char String_string[] = "String";
const char IO_string[] = "IO";
const char default_string[] = "";
Object* Object_new()
{
Object* o = (Object *) malloc(sizeof(Object));
if (o == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
o->vtblptr = &_Object_vtable_prototype;
return o;
}
Object* Object_abort(Object* self)
{
printf("Abort called from class %s\n",
!self ? "Unknown" : self->vtblptr->name);
exit(1);
return self;
}
String* Object_type_name(Object* self)
{
if (self == 0) {
fprintf(stderr, "At %s(line %d): self is NULL\n", __FILE__, __LINE__);
abort();
}
String* s = String_new();
s->val = self->vtblptr->name;
return s;
}
Object* Object_copy(Object* self)
{
if (self == 0) {
fprintf(stderr, "At %s(line %d): self is NULL\n", __FILE__, __LINE__);
abort();
}
unsigned size = self->vtblptr->size;
assert(size > 0);
Object* obj = (Object *) malloc(size);
if (obj == 0) {
fprintf(stderr, "At %s(line %d): malloc failed in Object::copy()\n",
__FILE__, __LINE__);
abort();
}
memcpy(obj, self, size);
return obj;
}
IO* IO_new()
{
IO* io = (IO *) malloc(sizeof(IO));
if (io == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
io->vtblptr = &_IO_vtable_prototype;
return io;
}
IO* IO_out_string(IO* self, String* s)
{
if (self == 0 || s == 0) {
fprintf(stderr, "At %s(line %d): NULL object\n", __FILE__, __LINE__);
abort();
}
printf("%s", s->val);
return self;
}
IO* IO_out_int(IO* self, int x)
{
if (self == 0) {
fprintf(stderr, "At %s(line %d): NULL object\n", __FILE__, __LINE__);
abort();
}
printf("%d", x);
return self;
}
static int get_one_line(char** in_string_p, FILE* stream)
{
size_t len = 0;
ssize_t num_chars_read;
num_chars_read = getline(in_string_p, &len, stdin);
if (*in_string_p == 0) {
fprintf(
stderr, "At %s(line %d): allocation failed in IO::in_string()\n",
__FILE__, __LINE__);
exit(1);
}
if (num_chars_read > 0 && (*in_string_p)[num_chars_read - 1] == '\n') {
(*in_string_p)[num_chars_read - 1] = '\0';
--len;
}
return len;
}
String* IO_in_string(IO* self)
{
if (self == 0) {
fprintf(stderr, "At %s(line %d): self is NULL\n", __FILE__, __LINE__);
abort();
}
char* in_string = 0;
ssize_t len = get_one_line(&in_string, stdin);
assert(in_string);
String* str = String_new();
str->val = in_string;
return str;
}
int IO_in_int(IO* self)
{
if (self == 0) {
fprintf(stderr, "At %s(line %d): self is NULL\n", __FILE__, __LINE__);
abort();
}
char* in_string = 0;
ssize_t len = get_one_line(&in_string, stdin);
assert(in_string);
int x;
int num_ints = 0;
if (len)
num_ints = sscanf(in_string, " %d", &x);
if (num_ints == 0) {
fprintf(stderr,
"At %s(line %d): Invalid integer on input in IO::in_int()\n",
__FILE__, __LINE__);
Object_abort((Object *) self);
}
return x;
}
Int* Int_new()
{
Int* x = (Int *) malloc(sizeof(Int));
if (x == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
x->vtblptr = &_Int_vtable_prototype;
x->val = 0;
return x;
}
void Int_init(Int* self, int i) { self->val = i; }
Bool* Bool_new()
{
Bool* b = (Bool *) malloc(sizeof(Bool));
if (b == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
b->vtblptr = &_Bool_vtable_prototype;
b->val = false;
return b;
}
void Bool_init(Bool* self, bool b) { self->val = b; }
String* String_new()
{
String* s = (String *) malloc(sizeof(String));
if (s == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
s->vtblptr = &_String_vtable_prototype;
s->val = "";
return s;
}
int String_length(String* self)
{
if (self == 0) {
fprintf(stderr, "At %s(line %d): self is NULL\n", __FILE__, __LINE__);
abort();
}
return strlen(self->val);
}
String* String_concat(String* self, String* s)
{
if (self == 0 || s == 0) {
fprintf(stderr, "At %s(line %d): NULL object\n", __FILE__, __LINE__);
abort();
}
String* s1 = (String *) malloc(sizeof(String));
if (s1 == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
s1->vtblptr = &_String_vtable_prototype;
char* cats = (char *) malloc(strlen(self->val) + strlen(s->val) + 1);
if (cats == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
strcpy(cats, self->val);
strcat(cats, s->val);
s1->val = cats;
return s1;
}
String* String_substr(String* self, int i, int l)
{
if (self == 0) {
fprintf(stderr, "At %s(line %d): self is NULL\n", __FILE__, __LINE__);
abort();
}
int len = strlen(self->val);
if (i >= len || i + l - 1 >= len) {
fprintf(stderr, "At %s(line %d): Substring out of range\n", __FILE__,
__LINE__);
Object_abort((Object *) 0);
}
String* s1 = (String *) malloc(sizeof(String));
if (s1 == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
s1->vtblptr = &_String_vtable_prototype;
char* subs = (char *) malloc(l + 1);
if (subs == 0) {
fprintf(stderr, "At %s(line %d): Out of memory\n", __FILE__, __LINE__);
Object_abort((Object *) 0);
}
strncpy(subs, &(self->val[i]), l);
subs[l] = '\0';
s1->val = subs;
return s1;
}