@@ -281,14 +281,17 @@ namespace rt::core
281
281
: objects::DynObject(cownPrototypeObject(), objects::cown_region)
282
282
{
283
283
status = Status::Pending;
284
- auto region = objects::get_region (obj);
284
+ auto old = set (" value" , obj);
285
+ assert (!old);
286
+ }
285
287
286
- if (!obj->is_immutable () && !obj->is_cown ())
287
- {
288
- // TODO: Make sure we're parenting the region and add third state, like
289
- // pending
290
- // Staring in an aquired state will allow the normal usage of `set`
288
+ [[nodiscard]] DynObject* set (std::string name, DynObject* obj) override
289
+ {
290
+ assert_modifiable ();
291
291
292
+ if (obj && !obj->is_immutable () && !obj->is_cown ())
293
+ {
294
+ auto region = objects::get_region (obj);
292
295
// Potentiall error message
293
296
std::stringstream ss;
294
297
ss << " Object is neither immutable nor a cown, attempted to threat it "
@@ -307,16 +310,23 @@ namespace rt::core
307
310
<< region->parent ->bridge ;
308
311
ui::error (ss.str (), {this , " " , obj});
309
312
}
313
+
314
+ region->cown = this ;
310
315
}
311
316
312
- auto old = set ( " value " , obj) ;
313
- assert (!old) ;
317
+ DynObject* old = fields[name] ;
318
+ fields[name] = obj ;
314
319
315
- // 1x LRC from the stack
316
- if (region->local_reference_count == 1 )
320
+ if (old && !old->is_immutable () && !old->is_cown ())
317
321
{
318
- status = Status::Released;
322
+ auto old_reg = objects::get_region (old);
323
+ assert (old_reg->cown == this );
324
+ old_reg->cown = nullptr ;
319
325
}
326
+
327
+ update_status ();
328
+
329
+ return old;
320
330
}
321
331
322
332
std::string get_name () override
@@ -346,6 +356,34 @@ namespace rt::core
346
356
return true ;
347
357
}
348
358
}
359
+
360
+ bool is_released ()
361
+ {
362
+ return this ->status == Status::Released;
363
+ }
364
+
365
+ // / This function updates the status of the cown. It mainly checks if a
366
+ // / cown in the pending state can be released.
367
+ void update_status ()
368
+ {
369
+ if (status != Status::Pending)
370
+ {
371
+ return ;
372
+ }
373
+
374
+ auto value = this ->get (" value" ).value ();
375
+ if (!value || value->is_immutable () || value->is_cown ())
376
+ {
377
+ status = Status::Released;
378
+ return ;
379
+ }
380
+
381
+ auto region = objects::get_region (value);
382
+ if (region->combined_lrc () == 0 )
383
+ {
384
+ status = Status::Released;
385
+ }
386
+ }
349
387
};
350
388
351
389
inline std::set<objects::DynObject*>* globals ()
0 commit comments