bool hasNonConstPointers(Expression *e) { if (e->type->ty == Terror) return false; if (e->op == TOKnull) return false; if (e->op == TOKstructliteral) { StructLiteralExp *se = (StructLiteralExp *)e; return arrayHasNonConstPointers(se->elements); } if (e->op == TOKarrayliteral) { if (!e->type->nextOf()->hasPointers()) return false; ArrayLiteralExp *ae = (ArrayLiteralExp *)e; return arrayHasNonConstPointers(ae->elements); } if (e->op == TOKassocarrayliteral) { AssocArrayLiteralExp *ae = (AssocArrayLiteralExp *)e; if (ae->type->nextOf()->hasPointers() && arrayHasNonConstPointers(ae->values)) return true; if (((TypeAArray *)ae->type)->index->hasPointers()) return arrayHasNonConstPointers(ae->keys); return false; } if (e->type->ty== Tpointer && e->type->nextOf()->ty != Tfunction) { #if IN_LLVM // address of a global is OK if (e->op == TOKaddress || e->op == TOKcast) return false; if (e->op == TOKadd || e->op == TOKmin) { BinExp *be = (BinExp*)e; if (be->e1->type->ty == Tpointer || be->e2->type->ty == Tpointer) return false; } #else if (e->op == TOKsymoff) // address of a global is OK return false; #endif if (e->op == TOKint64) // cast(void *)int is OK return false; if (e->op == TOKstring) // "abc".ptr is OK return false; return true; } return false; }
bool hasNonConstPointers(Expression *e) { if (e->type->ty == Terror) return false; if (e->op == TOKnull) return false; if (e->op == TOKstructliteral) { StructLiteralExp *se = (StructLiteralExp *)e; return arrayHasNonConstPointers(se->elements); } if (e->op == TOKarrayliteral) { if (!e->type->nextOf()->hasPointers()) return false; ArrayLiteralExp *ae = (ArrayLiteralExp *)e; return arrayHasNonConstPointers(ae->elements); } if (e->op == TOKassocarrayliteral) { AssocArrayLiteralExp *ae = (AssocArrayLiteralExp *)e; if (ae->type->nextOf()->hasPointers() && arrayHasNonConstPointers(ae->values)) return true; if (((TypeAArray *)ae->type)->index->hasPointers()) return arrayHasNonConstPointers(ae->keys); return false; } if(e->op == TOKaddress) { AddrExp *ae = (AddrExp *)e; if (ae->e1->op == TOKstructliteral) { StructLiteralExp *se = (StructLiteralExp *)ae->e1; if (!(se->stageflags & stageSearchPointers)) { int old = se->stageflags; se->stageflags |= stageSearchPointers; bool ret = arrayHasNonConstPointers(se->elements); se->stageflags = old; return ret; } else { return false; } } return true; } if (e->type->ty== Tpointer && e->type->nextOf()->ty != Tfunction) { if (e->op == TOKsymoff) // address of a global is OK return false; if (e->op == TOKint64) // cast(void *)int is OK return false; if (e->op == TOKstring) // "abc".ptr is OK return false; return true; } return false; }