@@ -220,7 +220,8 @@ fn (mut g Gen) str_val(node ast.StringInterLiteral, i int, fmts []u8) {
220220 g.write2 ('${dot} _object' , ')' )
221221 } else if fmt == `s` || typ.has_flag (.variadic) {
222222 mut exp_typ := typ
223- if expr is ast.Ident {
223+ is_comptime_for_var := expr is ast.Ident && g.is_comptime_for_var (expr)
224+ if ! is_comptime_for_var && expr is ast.Ident {
224225 if g.comptime.get_ct_type_var (expr) == .smartcast {
225226 exp_typ = g.type_resolver.get_type (expr)
226227 } else if expr.obj is ast.Var {
@@ -236,7 +237,17 @@ fn (mut g Gen) str_val(node ast.StringInterLiteral, i int, fmts []u8) {
236237 }
237238 }
238239 }
239- g.gen_expr_to_string (expr, exp_typ)
240+ if exp_typ.has_flag (.option) && expr is ast.Ident && g.is_comptime_for_var (expr) {
241+ str_fn_name := g.get_str_fn (exp_typ.clear_flag (.option))
242+ g.write ('${str_fn_name} (*(${g.base_type(exp_typ)} *)(' )
243+ old_inside_opt_or_res := g.inside_opt_or_res
244+ g.inside_opt_or_res = true
245+ g.expr (expr)
246+ g.inside_opt_or_res = old_inside_opt_or_res
247+ g.write ('.data))' )
248+ } else {
249+ g.gen_expr_to_string (expr, exp_typ)
250+ }
240251 } else if typ.is_number () || typ.is_pointer () || fmt == `d` {
241252 if typ.is_signed () && fmt in [`x` , `X` , `o` ] {
242253 // convert to unsigned first befors C's integer propagation strikes
@@ -283,26 +294,26 @@ fn (mut g Gen) string_inter_literal(node ast.StringInterLiteral) {
283294 mut node_ := unsafe { node }
284295 mut fmts := node_.fmts.clone ()
285296 for i, mut expr in node_.exprs {
286- mut type_to_use := node_.expr_types[i]
297+ mut field_typ := if mut expr is ast.Ident && g.is_comptime_for_var (expr) {
298+ g.comptime.comptime_for_field_type
299+ } else {
300+ node_.expr_types[i]
301+ }
287302 if g.comptime.inside_comptime_for && mut expr is ast.SelectorExpr {
288303 if expr.expr is ast.TypeOf && expr.field_name == 'name' {
289- // This is typeof(var).name
290304 typeof_expr := expr.expr as ast.TypeOf
291305 if typeof_expr.expr is ast.Ident {
292306 ident_name := (typeof_expr.expr as ast.Ident ).name
293- // Check if this ident might be from a multi-return in the current scope
294- // For now, force re-evaluation by looking it up in the comptime context
295307 if obj := typeof_expr.expr.scope.find (ident_name) {
296308 if obj is ast.Var {
297- // Use the var's actual type, which might be correct in codegen context
298- type_to_use = obj.typ
309+ field_typ = obj.typ
299310 }
300311 }
301312 }
302313 }
303314 }
304- if g.comptime.is_comptime (expr) {
305- ctyp := g.type_resolver.get_type_or_default (expr, node_.expr_types[i] )
315+ if g.comptime.is_comptime (expr) || (g.comptime.inside_comptime_for && expr is ast.Ident ) {
316+ ctyp := g.type_resolver.get_type_or_default (expr, field_typ )
306317 if ctyp != ast.void_type {
307318 node_.expr_types[i] = ctyp
308319 if node_.fmts[i] == `_` {
@@ -316,7 +327,7 @@ fn (mut g Gen) string_inter_literal(node ast.StringInterLiteral) {
316327 }
317328 }
318329 } else {
319- node_.expr_types[i] = type_to_use
330+ node_.expr_types[i] = field_typ
320331 }
321332 }
322333 g.write2 ('builtin__str_intp(' , node.vals.len.str ())
0 commit comments