mirror of
https://github.com/golang/go
synced 2024-10-04 05:21:22 -06:00
aa347c4a0d
and delete some dead code. no actual changes here. R=ken OCL=32764 CL=32764
88 lines
1.7 KiB
C
88 lines
1.7 KiB
C
// 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.
|
|
|
|
#include "go.h"
|
|
|
|
/*
|
|
* look for
|
|
* unsafe.Sizeof
|
|
* unsafe.Offsetof
|
|
* rewrite with a constant
|
|
*/
|
|
Node*
|
|
unsafenmagic(Node *fn, NodeList *args)
|
|
{
|
|
Node *r, *n;
|
|
Sym *s;
|
|
Type *t, *tr;
|
|
long v;
|
|
Val val;
|
|
|
|
if(fn == N || fn->op != ONAME || (s = fn->sym) == S)
|
|
goto no;
|
|
if(strcmp(s->package, "unsafe") != 0)
|
|
goto no;
|
|
|
|
if(args == nil) {
|
|
yyerror("missing argument for %S", s);
|
|
goto no;
|
|
}
|
|
r = args->n;
|
|
|
|
n = nod(OLITERAL, N, N);
|
|
if(strcmp(s->name, "Sizeof") == 0) {
|
|
typecheck(&r, Erv);
|
|
tr = r->type;
|
|
if(r->op == OLITERAL && r->val.ctype == CTSTR)
|
|
tr = types[TSTRING];
|
|
if(tr == T)
|
|
goto no;
|
|
v = tr->width;
|
|
goto yes;
|
|
}
|
|
if(strcmp(s->name, "Offsetof") == 0) {
|
|
if(r->op != ODOT && r->op != ODOTPTR)
|
|
goto no;
|
|
typecheck(&r, Erv);
|
|
v = r->xoffset;
|
|
goto yes;
|
|
}
|
|
if(strcmp(s->name, "Alignof") == 0) {
|
|
typecheck(&r, Erv);
|
|
tr = r->type;
|
|
if(r->op == OLITERAL && r->val.ctype == CTSTR)
|
|
tr = types[TSTRING];
|
|
if(tr == T)
|
|
goto no;
|
|
|
|
// make struct { byte; T; }
|
|
t = typ(TSTRUCT);
|
|
t->type = typ(TFIELD);
|
|
t->type->type = types[TUINT8];
|
|
t->type->down = typ(TFIELD);
|
|
t->type->down->type = tr;
|
|
// compute struct widths
|
|
dowidth(t);
|
|
|
|
// the offset of T is its required alignment
|
|
v = t->type->down->width;
|
|
goto yes;
|
|
}
|
|
|
|
no:
|
|
return N;
|
|
|
|
yes:
|
|
if(args->next != nil)
|
|
yyerror("extra arguments for %S", s);
|
|
// any side effects disappear; ignore init
|
|
val.ctype = CTINT;
|
|
val.u.xval = mal(sizeof(*n->val.u.xval));
|
|
mpmovecfix(val.u.xval, v);
|
|
n = nod(OLITERAL, N, N);
|
|
n->val = val;
|
|
n->type = types[TINT];
|
|
return n;
|
|
}
|