2009-01-14 09:21:25 -07:00
|
|
|
// Copyright 2009 The Go Authors. All rights reserved.
|
|
|
|
// Use of this source code is governed by a BSD-style
|
|
|
|
// license that can be found in the LICENSE file.
|
|
|
|
|
|
|
|
/* Translate a .cgo file into a .c file. A .cgo file is a combination
|
|
|
|
of a limited form of Go with C. */
|
|
|
|
|
|
|
|
/*
|
|
|
|
package PACKAGENAME
|
|
|
|
{# line}
|
|
|
|
func NAME([NAME TYPE { , NAME TYPE }]) [(NAME TYPE { , NAME TYPE })] \{
|
|
|
|
C code with proper brace nesting
|
|
|
|
\}
|
|
|
|
*/
|
|
|
|
|
|
|
|
/* We generate C code which implements the function such that it can
|
|
|
|
be called from Go and executes the C code. */
|
|
|
|
|
|
|
|
#include <assert.h>
|
|
|
|
#include <ctype.h>
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <string.h>
|
2009-01-22 17:23:44 -07:00
|
|
|
#include <errno.h>
|
2009-01-14 09:21:25 -07:00
|
|
|
|
2009-01-22 17:23:44 -07:00
|
|
|
/* Whether we're emitting for gcc */
|
|
|
|
static int gcc;
|
2009-01-14 09:21:25 -07:00
|
|
|
|
2009-01-22 17:23:44 -07:00
|
|
|
/* File and line number */
|
|
|
|
static const char *file;
|
2009-01-14 09:21:25 -07:00
|
|
|
static unsigned int lineno;
|
|
|
|
|
|
|
|
/* List of names and types. */
|
|
|
|
struct params {
|
|
|
|
struct params *next;
|
|
|
|
char *name;
|
|
|
|
char *type;
|
|
|
|
};
|
|
|
|
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
/* index into type_table */
|
|
|
|
enum {
|
|
|
|
Bool,
|
|
|
|
Float,
|
|
|
|
Int,
|
|
|
|
Uint,
|
|
|
|
Uintptr,
|
|
|
|
String,
|
2009-08-25 16:54:25 -06:00
|
|
|
Slice,
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
};
|
|
|
|
|
|
|
|
static struct {
|
|
|
|
char *name;
|
|
|
|
int size;
|
|
|
|
} type_table[] = {
|
|
|
|
/* variable sized first, for easy replacement */
|
|
|
|
/* order matches enum above */
|
|
|
|
/* default is 32-bit architecture sizes */
|
|
|
|
"bool", 1,
|
|
|
|
"float", 4,
|
|
|
|
"int", 4,
|
|
|
|
"uint", 4,
|
|
|
|
"uintptr", 4,
|
|
|
|
"String", 8,
|
2009-08-25 16:54:25 -06:00
|
|
|
"Slice", 12,
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
|
|
|
|
/* fixed size */
|
|
|
|
"float32", 4,
|
|
|
|
"float64", 8,
|
|
|
|
"byte", 1,
|
|
|
|
"int8", 1,
|
|
|
|
"uint8", 1,
|
|
|
|
"int16", 2,
|
|
|
|
"uint16", 2,
|
|
|
|
"int32", 4,
|
|
|
|
"uint32", 4,
|
|
|
|
"int64", 8,
|
|
|
|
"uint64", 8,
|
|
|
|
|
|
|
|
NULL,
|
|
|
|
};
|
|
|
|
|
|
|
|
/* Fixed structure alignment (non-gcc only) */
|
|
|
|
int structround = 4;
|
|
|
|
|
2009-01-14 09:21:25 -07:00
|
|
|
/* Unexpected EOF. */
|
|
|
|
static void
|
|
|
|
bad_eof(void)
|
|
|
|
{
|
2009-01-22 17:23:44 -07:00
|
|
|
fprintf(stderr, "%s:%u: unexpected EOF\n", file, lineno);
|
2009-01-14 09:21:25 -07:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Out of memory. */
|
|
|
|
static void
|
|
|
|
bad_mem(void)
|
|
|
|
{
|
2009-01-22 17:23:44 -07:00
|
|
|
fprintf(stderr, "%s:%u: out of memory\n", file, lineno);
|
2009-01-14 09:21:25 -07:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Allocate memory without fail. */
|
|
|
|
static void *
|
|
|
|
xmalloc(unsigned int size)
|
|
|
|
{
|
|
|
|
void *ret = malloc(size);
|
|
|
|
if (ret == NULL)
|
|
|
|
bad_mem();
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Reallocate memory without fail. */
|
|
|
|
static void*
|
|
|
|
xrealloc(void *buf, unsigned int size)
|
|
|
|
{
|
|
|
|
void *ret = realloc(buf, size);
|
|
|
|
if (ret == NULL)
|
|
|
|
bad_mem();
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Free a list of parameters. */
|
|
|
|
static void
|
|
|
|
free_params(struct params *p)
|
|
|
|
{
|
|
|
|
while (p != NULL) {
|
|
|
|
struct params *next;
|
|
|
|
|
|
|
|
next = p->next;
|
|
|
|
free(p->name);
|
|
|
|
free(p->type);
|
|
|
|
free(p);
|
|
|
|
p = next;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read a character, tracking lineno. */
|
|
|
|
static int
|
|
|
|
getchar_update_lineno(void)
|
|
|
|
{
|
|
|
|
int c;
|
|
|
|
|
|
|
|
c = getchar();
|
|
|
|
if (c == '\n')
|
|
|
|
++lineno;
|
|
|
|
return c;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read a character, giving an error on EOF, tracking lineno. */
|
|
|
|
static int
|
|
|
|
getchar_no_eof(void)
|
|
|
|
{
|
|
|
|
int c;
|
|
|
|
|
|
|
|
c = getchar_update_lineno();
|
|
|
|
if (c == EOF)
|
|
|
|
bad_eof();
|
|
|
|
return c;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read a character, skipping comments. */
|
|
|
|
static int
|
|
|
|
getchar_skipping_comments(void)
|
|
|
|
{
|
|
|
|
int c;
|
|
|
|
|
|
|
|
while (1) {
|
|
|
|
c = getchar_update_lineno();
|
|
|
|
if (c != '/')
|
|
|
|
return c;
|
|
|
|
|
|
|
|
c = getchar();
|
|
|
|
if (c == '/') {
|
|
|
|
do {
|
|
|
|
c = getchar_update_lineno();
|
|
|
|
} while (c != EOF && c != '\n');
|
|
|
|
return c;
|
|
|
|
} else if (c == '*') {
|
|
|
|
while (1) {
|
|
|
|
c = getchar_update_lineno();
|
|
|
|
if (c == EOF)
|
|
|
|
return EOF;
|
|
|
|
if (c == '*') {
|
|
|
|
do {
|
|
|
|
c = getchar_update_lineno();
|
|
|
|
} while (c == '*');
|
|
|
|
if (c == '/')
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
ungetc(c, stdin);
|
|
|
|
return '/';
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read and return a token. Tokens are delimited by whitespace or by
|
|
|
|
[(),{}]. The latter are all returned as single characters. */
|
|
|
|
static char *
|
|
|
|
read_token(void)
|
|
|
|
{
|
|
|
|
int c;
|
|
|
|
char *buf;
|
|
|
|
unsigned int alc, off;
|
|
|
|
const char* delims = "(),{}";
|
|
|
|
|
|
|
|
while (1) {
|
|
|
|
c = getchar_skipping_comments();
|
|
|
|
if (c == EOF)
|
|
|
|
return NULL;
|
|
|
|
if (!isspace(c))
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
alc = 16;
|
|
|
|
buf = xmalloc(alc + 1);
|
|
|
|
off = 0;
|
|
|
|
if (strchr(delims, c) != NULL) {
|
|
|
|
buf[off] = c;
|
|
|
|
++off;
|
|
|
|
} else {
|
|
|
|
while (1) {
|
|
|
|
if (off >= alc) {
|
|
|
|
alc *= 2;
|
|
|
|
buf = xrealloc(buf, alc + 1);
|
|
|
|
}
|
|
|
|
buf[off] = c;
|
|
|
|
++off;
|
|
|
|
c = getchar_skipping_comments();
|
|
|
|
if (c == EOF)
|
|
|
|
break;
|
|
|
|
if (isspace(c) || strchr(delims, c) != NULL) {
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
if (c == '\n')
|
|
|
|
lineno--;
|
2009-01-14 09:21:25 -07:00
|
|
|
ungetc(c, stdin);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
buf[off] = '\0';
|
|
|
|
return buf;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read a token, giving an error on EOF. */
|
|
|
|
static char *
|
|
|
|
read_token_no_eof(void)
|
|
|
|
{
|
|
|
|
char *token = read_token();
|
|
|
|
if (token == NULL)
|
|
|
|
bad_eof();
|
|
|
|
return token;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read the package clause, and return the package name. */
|
|
|
|
static char *
|
|
|
|
read_package(void)
|
|
|
|
{
|
|
|
|
char *token;
|
|
|
|
|
|
|
|
token = read_token_no_eof();
|
|
|
|
if (strcmp(token, "package") != 0) {
|
|
|
|
fprintf(stderr,
|
2009-01-22 17:23:44 -07:00
|
|
|
"%s:%u: expected \"package\", got \"%s\"\n",
|
|
|
|
file, lineno, token);
|
2009-01-14 09:21:25 -07:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
return read_token_no_eof();
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read and copy preprocessor lines. */
|
|
|
|
static void
|
|
|
|
read_preprocessor_lines(void)
|
|
|
|
{
|
|
|
|
while (1) {
|
|
|
|
int c;
|
|
|
|
|
|
|
|
do {
|
|
|
|
c = getchar_skipping_comments();
|
|
|
|
} while (isspace(c));
|
|
|
|
if (c != '#') {
|
|
|
|
ungetc(c, stdin);
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
break;
|
2009-01-14 09:21:25 -07:00
|
|
|
}
|
|
|
|
putchar(c);
|
|
|
|
do {
|
|
|
|
c = getchar_update_lineno();
|
|
|
|
putchar(c);
|
|
|
|
} while (c != '\n');
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read a type in Go syntax and return a type in C syntax. We only
|
|
|
|
permit basic types and pointers. */
|
|
|
|
static char *
|
|
|
|
read_type(void)
|
|
|
|
{
|
|
|
|
char *p, *op, *q;
|
|
|
|
int pointer_count;
|
|
|
|
unsigned int len;
|
|
|
|
|
|
|
|
p = read_token_no_eof();
|
|
|
|
if (*p != '*')
|
|
|
|
return p;
|
|
|
|
op = p;
|
|
|
|
pointer_count = 0;
|
|
|
|
while (*p == '*') {
|
|
|
|
++pointer_count;
|
|
|
|
++p;
|
|
|
|
}
|
|
|
|
len = strlen(p);
|
|
|
|
q = xmalloc(len + pointer_count + 1);
|
|
|
|
memcpy(q, p, len);
|
|
|
|
while (pointer_count > 0) {
|
|
|
|
q[len] = '*';
|
|
|
|
++len;
|
|
|
|
--pointer_count;
|
|
|
|
}
|
|
|
|
q[len] = '\0';
|
|
|
|
free(op);
|
|
|
|
return q;
|
|
|
|
}
|
|
|
|
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
/* Return the size of the given type. */
|
|
|
|
static int
|
|
|
|
type_size(char *p)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
|
|
|
|
if(p[strlen(p)-1] == '*')
|
|
|
|
return type_table[Uintptr].size;
|
|
|
|
|
|
|
|
for(i=0; type_table[i].name; i++)
|
|
|
|
if(strcmp(type_table[i].name, p) == 0)
|
|
|
|
return type_table[i].size;
|
|
|
|
fprintf(stderr, "%s:%u: unknown type %s\n", file, lineno, p);
|
|
|
|
exit(1);
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2009-01-14 09:21:25 -07:00
|
|
|
/* Read a list of parameters. Each parameter is a name and a type.
|
|
|
|
The list ends with a ')'. We have already read the '('. */
|
|
|
|
static struct params *
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
read_params(int *poffset)
|
2009-01-14 09:21:25 -07:00
|
|
|
{
|
|
|
|
char *token;
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
struct params *ret, **pp, *p;
|
|
|
|
int offset, size, rnd;
|
2009-01-14 09:21:25 -07:00
|
|
|
|
|
|
|
ret = NULL;
|
|
|
|
pp = &ret;
|
|
|
|
token = read_token_no_eof();
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
offset = 0;
|
2009-01-14 09:21:25 -07:00
|
|
|
if (strcmp(token, ")") != 0) {
|
|
|
|
while (1) {
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
p = xmalloc(sizeof(struct params));
|
|
|
|
p->name = token;
|
|
|
|
p->type = read_type();
|
|
|
|
p->next = NULL;
|
|
|
|
*pp = p;
|
|
|
|
pp = &p->next;
|
|
|
|
|
|
|
|
size = type_size(p->type);
|
|
|
|
rnd = size;
|
|
|
|
if(rnd > structround)
|
|
|
|
rnd = structround;
|
|
|
|
if(offset%rnd)
|
|
|
|
offset += rnd - offset%rnd;
|
|
|
|
offset += size;
|
2009-01-14 09:21:25 -07:00
|
|
|
|
|
|
|
token = read_token_no_eof();
|
|
|
|
if (strcmp(token, ",") != 0)
|
|
|
|
break;
|
|
|
|
token = read_token_no_eof();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (strcmp(token, ")") != 0) {
|
2009-01-22 17:23:44 -07:00
|
|
|
fprintf(stderr, "%s:%u: expected '('\n",
|
|
|
|
file, lineno);
|
2009-01-14 09:21:25 -07:00
|
|
|
exit(1);
|
|
|
|
}
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
if (poffset != NULL)
|
|
|
|
*poffset = offset;
|
2009-01-14 09:21:25 -07:00
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read a function header. This reads up to and including the initial
|
|
|
|
'{' character. Returns 1 if it read a header, 0 at EOF. */
|
|
|
|
static int
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
read_func_header(char **name, struct params **params, int *paramwid, struct params **rets)
|
2009-01-14 09:21:25 -07:00
|
|
|
{
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
int lastline;
|
2009-01-14 09:21:25 -07:00
|
|
|
char *token;
|
|
|
|
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
lastline = -1;
|
|
|
|
while (1) {
|
|
|
|
token = read_token();
|
|
|
|
if (token == NULL)
|
|
|
|
return 0;
|
|
|
|
if (strcmp(token, "func") == 0) {
|
|
|
|
if(lastline != -1)
|
|
|
|
printf("\n");
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (lastline != lineno) {
|
|
|
|
if (lastline == lineno-1)
|
|
|
|
printf("\n");
|
|
|
|
else
|
|
|
|
printf("\n#line %d \"%s\"\n", lineno, file);
|
|
|
|
lastline = lineno;
|
|
|
|
}
|
|
|
|
printf("%s ", token);
|
2009-01-14 09:21:25 -07:00
|
|
|
}
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
|
2009-01-14 09:21:25 -07:00
|
|
|
*name = read_token_no_eof();
|
|
|
|
|
|
|
|
token = read_token();
|
|
|
|
if (token == NULL || strcmp(token, "(") != 0) {
|
2009-01-22 17:23:44 -07:00
|
|
|
fprintf(stderr, "%s:%u: expected \"(\"\n",
|
|
|
|
file, lineno);
|
2009-01-14 09:21:25 -07:00
|
|
|
exit(1);
|
|
|
|
}
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
*params = read_params(paramwid);
|
2009-01-14 09:21:25 -07:00
|
|
|
|
|
|
|
token = read_token();
|
|
|
|
if (token == NULL || strcmp(token, "(") != 0)
|
|
|
|
*rets = NULL;
|
|
|
|
else {
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
*rets = read_params(NULL);
|
2009-01-14 09:21:25 -07:00
|
|
|
token = read_token();
|
|
|
|
}
|
|
|
|
if (token == NULL || strcmp(token, "{") != 0) {
|
2009-01-22 17:23:44 -07:00
|
|
|
fprintf(stderr, "%s:%u: expected \"{\"\n",
|
|
|
|
file, lineno);
|
2009-01-14 09:21:25 -07:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Write out parameters. */
|
|
|
|
static void
|
|
|
|
write_params(struct params *params, int *first)
|
|
|
|
{
|
|
|
|
struct params *p;
|
|
|
|
|
|
|
|
for (p = params; p != NULL; p = p->next) {
|
|
|
|
if (*first)
|
|
|
|
*first = 0;
|
|
|
|
else
|
|
|
|
printf(", ");
|
|
|
|
printf("%s %s", p->type, p->name);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Write a 6g function header. */
|
|
|
|
static void
|
|
|
|
write_6g_func_header(char *package, char *name, struct params *params,
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
int paramwid, struct params *rets)
|
2009-01-14 09:21:25 -07:00
|
|
|
{
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
int first, n;
|
2009-01-14 09:21:25 -07:00
|
|
|
|
|
|
|
printf("void\n%s·%s(", package, name);
|
|
|
|
first = 1;
|
|
|
|
write_params(params, &first);
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
|
|
|
|
/* insert padding to align output struct */
|
|
|
|
if(rets != NULL && paramwid%structround != 0) {
|
|
|
|
n = structround - paramwid%structround;
|
|
|
|
if(n & 1)
|
|
|
|
printf(", uint8");
|
|
|
|
if(n & 2)
|
|
|
|
printf(", uint16");
|
|
|
|
if(n & 4)
|
|
|
|
printf(", uint32");
|
|
|
|
}
|
|
|
|
|
2009-01-14 09:21:25 -07:00
|
|
|
write_params(rets, &first);
|
|
|
|
printf(")\n{\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Write a 6g function trailer. */
|
|
|
|
static void
|
|
|
|
write_6g_func_trailer(struct params *rets)
|
|
|
|
{
|
|
|
|
struct params *p;
|
|
|
|
|
|
|
|
for (p = rets; p != NULL; p = p->next)
|
|
|
|
printf("\tFLUSH(&%s);\n", p->name);
|
|
|
|
printf("}\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Define the gcc function return type if necessary. */
|
|
|
|
static void
|
|
|
|
define_gcc_return_type(char *package, char *name, struct params *rets)
|
|
|
|
{
|
|
|
|
struct params *p;
|
|
|
|
|
|
|
|
if (rets == NULL || rets->next == NULL)
|
|
|
|
return;
|
|
|
|
printf("struct %s_%s_ret {\n", package, name);
|
|
|
|
for (p = rets; p != NULL; p = p->next)
|
|
|
|
printf(" %s %s;\n", p->type, p->name);
|
|
|
|
printf("};\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Write out the gcc function return type. */
|
|
|
|
static void
|
|
|
|
write_gcc_return_type(char *package, char *name, struct params *rets)
|
|
|
|
{
|
|
|
|
if (rets == NULL)
|
|
|
|
printf("void");
|
|
|
|
else if (rets->next == NULL)
|
|
|
|
printf("%s", rets->type);
|
|
|
|
else
|
|
|
|
printf("struct %s_%s_ret", package, name);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Write out a gcc function header. */
|
|
|
|
static void
|
|
|
|
write_gcc_func_header(char *package, char *name, struct params *params,
|
|
|
|
struct params *rets)
|
|
|
|
{
|
|
|
|
int first;
|
|
|
|
struct params *p;
|
|
|
|
|
|
|
|
define_gcc_return_type(package, name, rets);
|
|
|
|
write_gcc_return_type(package, name, rets);
|
|
|
|
printf(" %s_%s(", package, name);
|
|
|
|
first = 1;
|
|
|
|
write_params(params, &first);
|
|
|
|
printf(") asm (\"%s.%s\");\n", package, name);
|
|
|
|
write_gcc_return_type(package, name, rets);
|
|
|
|
printf(" %s_%s(", package, name);
|
|
|
|
first = 1;
|
|
|
|
write_params(params, &first);
|
|
|
|
printf(")\n{\n");
|
|
|
|
for (p = rets; p != NULL; p = p->next)
|
|
|
|
printf(" %s %s;\n", p->type, p->name);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Write out a gcc function trailer. */
|
|
|
|
static void
|
|
|
|
write_gcc_func_trailer(char *package, char *name, struct params *rets)
|
|
|
|
{
|
|
|
|
if (rets == NULL)
|
|
|
|
;
|
|
|
|
else if (rets->next == NULL)
|
|
|
|
printf("return %s;\n", rets->name);
|
|
|
|
else {
|
|
|
|
struct params *p;
|
|
|
|
|
|
|
|
printf(" {\n struct %s_%s_ret __ret;\n", package, name);
|
|
|
|
for (p = rets; p != NULL; p = p->next)
|
|
|
|
printf(" __ret.%s = %s;\n", p->name, p->name);
|
|
|
|
printf(" return __ret;\n }\n");
|
|
|
|
}
|
|
|
|
printf("}\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Write out a function header. */
|
|
|
|
static void
|
2009-01-22 17:23:44 -07:00
|
|
|
write_func_header(char *package, char *name,
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
struct params *params, int paramwid,
|
|
|
|
struct params *rets)
|
2009-01-14 09:21:25 -07:00
|
|
|
{
|
2009-01-22 17:23:44 -07:00
|
|
|
if (gcc)
|
2009-01-14 09:21:25 -07:00
|
|
|
write_gcc_func_header(package, name, params, rets);
|
|
|
|
else
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
write_6g_func_header(package, name, params, paramwid, rets);
|
2009-01-22 17:23:44 -07:00
|
|
|
printf("#line %d \"%s\"\n", lineno, file);
|
2009-01-14 09:21:25 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
/* Write out a function trailer. */
|
|
|
|
static void
|
2009-01-22 17:23:44 -07:00
|
|
|
write_func_trailer(char *package, char *name,
|
2009-01-14 09:21:25 -07:00
|
|
|
struct params *rets)
|
|
|
|
{
|
2009-01-22 17:23:44 -07:00
|
|
|
if (gcc)
|
2009-01-14 09:21:25 -07:00
|
|
|
write_gcc_func_trailer(package, name, rets);
|
|
|
|
else
|
|
|
|
write_6g_func_trailer(rets);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Read and write the body of the function, ending in an unnested }
|
|
|
|
(which is read but not written). */
|
|
|
|
static void
|
2009-01-22 17:23:44 -07:00
|
|
|
copy_body(void)
|
2009-01-14 09:21:25 -07:00
|
|
|
{
|
|
|
|
int nesting = 0;
|
|
|
|
while (1) {
|
|
|
|
int c;
|
|
|
|
|
|
|
|
c = getchar_no_eof();
|
|
|
|
if (c == '}' && nesting == 0)
|
|
|
|
return;
|
|
|
|
putchar(c);
|
|
|
|
switch (c) {
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
case '{':
|
|
|
|
++nesting;
|
|
|
|
break;
|
|
|
|
case '}':
|
|
|
|
--nesting;
|
|
|
|
break;
|
|
|
|
case '/':
|
|
|
|
c = getchar_update_lineno();
|
|
|
|
putchar(c);
|
|
|
|
if (c == '/') {
|
|
|
|
do {
|
|
|
|
c = getchar_no_eof();
|
|
|
|
putchar(c);
|
|
|
|
} while (c != '\n');
|
|
|
|
} else if (c == '*') {
|
|
|
|
while (1) {
|
|
|
|
c = getchar_no_eof();
|
|
|
|
putchar(c);
|
|
|
|
if (c == '*') {
|
|
|
|
do {
|
|
|
|
c = getchar_no_eof();
|
|
|
|
putchar(c);
|
|
|
|
} while (c == '*');
|
|
|
|
if (c == '/')
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
case '"':
|
|
|
|
case '\'':
|
|
|
|
{
|
|
|
|
int delim = c;
|
|
|
|
do {
|
|
|
|
c = getchar_no_eof();
|
|
|
|
putchar(c);
|
|
|
|
if (c == '\\') {
|
|
|
|
c = getchar_no_eof();
|
|
|
|
putchar(c);
|
|
|
|
c = '\0';
|
|
|
|
}
|
|
|
|
} while (c != delim);
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Process the entire file. */
|
|
|
|
static void
|
2009-01-22 17:23:44 -07:00
|
|
|
process_file(void)
|
2009-01-14 09:21:25 -07:00
|
|
|
{
|
|
|
|
char *package, *name;
|
|
|
|
struct params *params, *rets;
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
int paramwid;
|
2009-01-14 09:21:25 -07:00
|
|
|
|
|
|
|
package = read_package();
|
|
|
|
read_preprocessor_lines();
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
while (read_func_header(&name, ¶ms, ¶mwid, &rets)) {
|
|
|
|
write_func_header(package, name, params, paramwid, rets);
|
2009-01-14 09:21:25 -07:00
|
|
|
copy_body();
|
2009-01-22 17:23:44 -07:00
|
|
|
write_func_trailer(package, name, rets);
|
2009-01-14 09:21:25 -07:00
|
|
|
free(name);
|
|
|
|
free_params(params);
|
|
|
|
free_params(rets);
|
|
|
|
}
|
|
|
|
free(package);
|
|
|
|
}
|
|
|
|
|
2009-01-22 17:23:44 -07:00
|
|
|
static void
|
|
|
|
usage(void)
|
|
|
|
{
|
|
|
|
fprintf(stderr, "Usage: cgo2c [--6g | --gc] [file]\n");
|
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
|
2009-01-14 09:21:25 -07:00
|
|
|
int
|
|
|
|
main(int argc, char **argv)
|
|
|
|
{
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
char *goarch;
|
|
|
|
|
2009-01-22 17:23:44 -07:00
|
|
|
while(argc > 1 && argv[1][0] == '-') {
|
|
|
|
if(strcmp(argv[1], "-") == 0)
|
|
|
|
break;
|
|
|
|
if(strcmp(argv[1], "--6g") == 0)
|
|
|
|
gcc = 0;
|
|
|
|
else if(strcmp(argv[1], "--gcc") == 0)
|
|
|
|
gcc = 1;
|
|
|
|
else
|
|
|
|
usage();
|
|
|
|
argc--;
|
|
|
|
argv++;
|
|
|
|
}
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
|
2009-01-22 17:23:44 -07:00
|
|
|
if(argc <= 1 || strcmp(argv[1], "-") == 0) {
|
|
|
|
file = "<stdin>";
|
|
|
|
process_file();
|
|
|
|
return 0;
|
|
|
|
}
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
|
2009-01-22 17:23:44 -07:00
|
|
|
if(argc > 2)
|
|
|
|
usage();
|
|
|
|
|
|
|
|
file = argv[1];
|
|
|
|
if(freopen(file, "r", stdin) == 0) {
|
|
|
|
fprintf(stderr, "open %s: %s\n", file, strerror(errno));
|
|
|
|
exit(1);
|
2009-01-14 09:21:25 -07:00
|
|
|
}
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
|
|
|
|
if(!gcc) {
|
|
|
|
// 6g etc; update size table
|
|
|
|
goarch = getenv("GOARCH");
|
|
|
|
if(goarch != NULL && strcmp(goarch, "amd64") == 0) {
|
|
|
|
type_table[Uintptr].size = 8;
|
|
|
|
type_table[String].size = 16;
|
2009-08-25 16:54:25 -06:00
|
|
|
type_table[Slice].size = 8+4+4;
|
in preparation for changing 6g's behavior to
align the output args separately from the input args,
change cgo2c to insert the necessary padding
when the two arg lists are concatenated in the c
translation.
for example, there is a runtime
func indexstring(s string, i int32) (b byte)
right now in 6g those arguments are aligned in one
struct with s at offset 0, i at 16, and b at 20.
soon the b byte will be in its own struct and structs
are 8 aligned, so it will be b at 24.
right now cgo2c generates:
void indexstring(string s, int32 i, byte b)
this CL makes it generate, in --6g mode:
void indexstring(string s, int32 i, uint32, byte b)
this is valid 6c input, although not valid gcc input.
(the code is being generated for 6c only anyway.)
also, allow C code to be mixed in among the Go funcs.
every instance of the token `func' is expected to start
a new go func.
R=iant
DELTA=145 (118 added, 0 deleted, 27 changed)
OCL=30949
CL=30963
2009-06-30 21:01:41 -06:00
|
|
|
structround = 8;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2009-01-22 17:23:44 -07:00
|
|
|
process_file();
|
2009-01-14 09:21:25 -07:00
|
|
|
return 0;
|
|
|
|
}
|