mirror of
https://github.com/urbit/shrub.git
synced 2024-12-22 18:31:44 +03:00
mutating edit
This commit is contained in:
parent
6ce5fb681e
commit
7dcc2303d1
@ -256,6 +256,15 @@
|
||||
? u3a_north_is_senior(r, som) \
|
||||
: u3a_south_is_senior(r, som) )
|
||||
|
||||
# define u3a_is_mutable(r, som) \
|
||||
( _(u3a_is_atom(som)) \
|
||||
? c3n \
|
||||
: _(u3a_is_senior(r, som)) \
|
||||
? c3n \
|
||||
: _(u3a_is_junior(r, som)) \
|
||||
? c3n \
|
||||
: (u3a_botox(u3a_to_ptr(som))->use_w == 1) \
|
||||
? c3y : c3n )
|
||||
|
||||
/** Globals.
|
||||
**/
|
||||
|
@ -55,6 +55,14 @@
|
||||
u3_noun
|
||||
u3i_qual(u3_noun a, u3_noun b, u3_noun c, u3_noun d);
|
||||
|
||||
/* u3i_edit():
|
||||
**
|
||||
** Mutate `big` at axis `axe` with new value `som`
|
||||
** `axe` is RETAINED.
|
||||
*/
|
||||
u3_noun
|
||||
u3i_edit(u3_noun big, u3_noun axe, u3_noun som);
|
||||
|
||||
/* u3i_string():
|
||||
**
|
||||
** Produce an LSB-first atom from the C string `a`.
|
||||
|
144
noun/imprison.c
144
noun/imprison.c
@ -262,6 +262,150 @@ u3i_qual(u3_noun a, u3_noun b, u3_noun c, u3_noun d)
|
||||
return u3i_cell(a, u3i_trel(b, c, d));
|
||||
}
|
||||
|
||||
static u3_noun
|
||||
_edit_cat(u3_noun big, c3_l axe_l, u3_noun som)
|
||||
{
|
||||
if ( c3n == u3du(big) ) {
|
||||
return u3m_bail(c3__exit);
|
||||
}
|
||||
else {
|
||||
u3_noun pro;
|
||||
switch ( axe_l ) {
|
||||
case 2:
|
||||
pro = u3nc(som, u3k(u3t(big)));
|
||||
break;
|
||||
case 3:
|
||||
pro = u3nc(u3k(u3h(big)), som);
|
||||
break;
|
||||
default: {
|
||||
c3_l mor_l = u3x_mas(axe_l);
|
||||
pro = ( 2 == u3x_cap(axe_l) )
|
||||
? u3nc(_edit_cat(u3k(u3h(big)), mor_l, som), u3k(u3t(big)))
|
||||
: u3nc(u3k(u3h(big)), _edit_cat(u3k(u3t(big)), mor_l, som));
|
||||
break;
|
||||
}
|
||||
}
|
||||
u3z(big);
|
||||
return pro;
|
||||
}
|
||||
}
|
||||
|
||||
static u3_noun
|
||||
_edit(u3_noun big, u3_noun axe, u3_noun som)
|
||||
{
|
||||
if ( c3y == u3a_is_cat(axe) ) {
|
||||
return _edit_cat(big, (c3_l) axe, som);
|
||||
}
|
||||
else if ( c3n == u3du(big) ) {
|
||||
return u3m_bail(c3__exit);
|
||||
}
|
||||
else {
|
||||
u3_noun mor = u3qc_mas(axe),
|
||||
pro = ( 2 == u3qc_cap(axe) )
|
||||
? u3nc(_edit(u3k(u3h(big)), mor, som), u3k(u3t(big)))
|
||||
: u3nc(u3k(u3h(big)), _edit(u3k(u3t(big)), mor, som));
|
||||
u3z(mor);
|
||||
u3z(big);
|
||||
return pro;
|
||||
}
|
||||
}
|
||||
|
||||
static u3_noun _edit_or_mutate_cat(u3_noun, c3_l, u3_noun);
|
||||
static u3_noun _edit_or_mutate(u3_noun, u3_noun, u3_noun);
|
||||
|
||||
static void
|
||||
_mutate_cat(u3_noun big, c3_l axe_l, u3_noun som)
|
||||
{
|
||||
if ( c3n == u3du(big) ) {
|
||||
u3m_bail(c3__exit);
|
||||
}
|
||||
else {
|
||||
u3a_cell* cel_u = (void*) u3a_to_ptr(big);
|
||||
switch ( axe_l ) {
|
||||
case 2:
|
||||
u3z(cel_u->hed);
|
||||
cel_u->hed = som;
|
||||
break;
|
||||
case 3:
|
||||
u3z(cel_u->tel);
|
||||
cel_u->tel = som;
|
||||
break;
|
||||
default: {
|
||||
u3_noun* tar = ( 2 == u3x_cap(axe_l) )
|
||||
? &(cel_u->hed)
|
||||
: &(cel_u->tel);
|
||||
*tar = _edit_or_mutate_cat(*tar, u3x_mas(axe_l), som);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
_mutate(u3_noun big, u3_noun axe, u3_noun som)
|
||||
{
|
||||
if ( c3y == u3a_is_cat(axe) ) {
|
||||
_mutate_cat(big, (c3_l) axe, som);
|
||||
}
|
||||
else if ( c3n == u3du(big) ) {
|
||||
u3m_bail(c3__exit);
|
||||
}
|
||||
else {
|
||||
u3a_cell* cel_u = (void*) u3a_to_ptr(big);
|
||||
u3_noun mor = u3qc_mas(axe);
|
||||
u3_noun* tar = ( 2 == u3qc_cap(axe) )
|
||||
? &(cel_u->hed)
|
||||
: &(cel_u->tel);
|
||||
*tar = _edit_or_mutate(*tar, mor, som);
|
||||
u3z(mor);
|
||||
}
|
||||
}
|
||||
|
||||
static u3_noun
|
||||
_edit_or_mutate_cat(u3_noun big, c3_l axe_l, u3_noun som)
|
||||
{
|
||||
if ( c3y == u3a_is_mutable(u3R, big) ) {
|
||||
_mutate_cat(big, axe_l, som);
|
||||
return big;
|
||||
}
|
||||
else {
|
||||
return _edit_cat(big, axe_l, som);
|
||||
}
|
||||
}
|
||||
|
||||
static u3_noun
|
||||
_edit_or_mutate(u3_noun big, u3_noun axe, u3_noun som)
|
||||
{
|
||||
if ( c3y == u3a_is_cat(axe) ) {
|
||||
return _edit_or_mutate_cat(big, (c3_l) axe, som);
|
||||
}
|
||||
else if ( c3y == u3a_is_mutable(u3R, big) ) {
|
||||
_mutate(big, axe, som);
|
||||
return big;
|
||||
}
|
||||
else {
|
||||
return _edit(big, axe, som);
|
||||
}
|
||||
}
|
||||
|
||||
/* u3i_edit():
|
||||
**
|
||||
** Mutate `big` at axis `axe` with new value `som`.
|
||||
** `axe` is RETAINED.
|
||||
*/
|
||||
u3_noun
|
||||
u3i_edit(u3_noun big, u3_noun axe, u3_noun som)
|
||||
{
|
||||
switch ( axe ) {
|
||||
case 0:
|
||||
return u3m_bail(c3__exit);
|
||||
case 1:
|
||||
u3z(big);
|
||||
return som;
|
||||
default:
|
||||
return _edit_or_mutate(big, axe, som);
|
||||
}
|
||||
}
|
||||
|
||||
/* u3i_string():
|
||||
**
|
||||
** Produce an LSB-first atom from the C string `a`.
|
||||
|
26
noun/nock.c
26
noun/nock.c
@ -1591,30 +1591,6 @@ _n_kale(u3_noun a)
|
||||
return a;
|
||||
}
|
||||
|
||||
|
||||
/* _n_edit(): PRODUCE a modified big with its axe axis
|
||||
* changed to som. axe is RETAINED.
|
||||
*/
|
||||
static u3_noun
|
||||
_n_edit(u3_noun big, u3_noun axe, u3_noun som)
|
||||
{
|
||||
if ( c3y == u3a_is_cat(axe) ) {
|
||||
return u3i_molt(big, axe, som, 0);
|
||||
}
|
||||
else {
|
||||
u3_noun mor = u3qc_mas(axe);
|
||||
if ( c3n == u3du(big) ) {
|
||||
u3m_bail(c3__exit);
|
||||
}
|
||||
u3_noun pro = ( 2 == u3qc_cap(axe) )
|
||||
? u3nc(_n_edit(u3k(u3h(big)), mor, som), u3k(u3t(big)))
|
||||
: u3nc(u3k(u3h(big)), _n_edit(u3k(u3t(big)), mor, som));
|
||||
u3z(mor);
|
||||
u3z(big);
|
||||
return pro;
|
||||
}
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
u3n_prog* pog_u;
|
||||
c3_w ip_w;
|
||||
@ -2325,7 +2301,7 @@ _n_burn(u3n_prog* pog_u, u3_noun bus, c3_ys mov, c3_ys off)
|
||||
_n_toss(mov, off);
|
||||
top = _n_peek(off);
|
||||
edit_in:
|
||||
*top = _n_edit(*top, x, o);
|
||||
*top = u3i_edit(*top, x, o);
|
||||
BURN();
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user