1
1
import { assert , details as X } from '@agoric/assert' ;
2
2
import buildCommsDispatch from '../src/vats/comms' ;
3
+ import { debugState } from '../src/vats/comms/dispatch' ;
3
4
import { flipRemoteSlot } from '../src/vats/comms/parseRemoteSlot' ;
4
5
5
6
// This module provides a power tool for testing the comms vat implementation.
@@ -58,7 +59,7 @@ import { flipRemoteSlot } from '../src/vats/comms/parseRemoteSlot';
58
59
//
59
60
// WHAT is a string of the form `${who}${dir}${op}`
60
61
// ${who} is the actor: 'k' (kernel) or 'a', 'b', or 'c' (remotes)
61
- // ${dir} is the direction: '>' (inject) or '<' (observe)
62
+ // ${dir} is the direction: '>' (inject), '<' (observe), or ':' (control )
62
63
// ${op} is the operation: 'm' (message), 'r' (resolve), 's' (subscribe), or 'l' (lag)
63
64
//
64
65
// OTHERSTUFF depends on ${op}:
@@ -85,7 +86,7 @@ import { flipRemoteSlot } from '../src/vats/comms/parseRemoteSlot';
85
86
// acknowledged DELAY deliveries (messages or resolutions) behind messages
86
87
// sent to the remote. The lag can be reduced to a lower value. It can
87
88
// also be turned off again with a DELAY of 0.
88
- // Lag is only allowed if ${who} is a remote and ${dir} is '> '
89
+ // Lag is only allowed if ${who} is a remote and ${dir} is ': '
89
90
//
90
91
// Any promise or object reference called for the in API above should be given
91
92
// as a string of the form `@REF` or `@REF:IFACE`. REF is a normal vat vref or
@@ -114,6 +115,10 @@ import { flipRemoteSlot } from '../src/vats/comms/parseRemoteSlot';
114
115
// describe. It will be a test failure if these do not match or if the log
115
116
// array is empty.
116
117
//
118
+ // A ':' (control) operation will alter the behavior of the simulation conducted
119
+ // by the vat driver framework. Currently the only control operation is 'l',
120
+ // which manipulates the lag of remotes.
121
+ //
117
122
// The `done()` function should be called at the end of the test, and will fail
118
123
// the test if the log array at that point is not empty.
119
124
//
@@ -168,7 +173,7 @@ function loggingSyscall(log) {
168
173
*
169
174
* @returns {string } the ref embedded within `scriptRef`
170
175
*/
171
- function refFromScriptRef ( scriptRef ) {
176
+ function refOf ( scriptRef ) {
172
177
assert (
173
178
scriptRef [ 0 ] === '@' ,
174
179
X `expected reference ${ scriptRef } to start with '@'` ,
@@ -183,6 +188,10 @@ function refFromScriptRef(scriptRef) {
183
188
return ref ;
184
189
}
185
190
191
+ function flipRefOf ( scriptRef ) {
192
+ return flipRemoteSlot ( refOf ( scriptRef ) ) ;
193
+ }
194
+
186
195
/**
187
196
* Extract the interface name embedded in a reference string as found in a test
188
197
* script. This will be a string of the form `@${ref}` or `@${ref}:${iface}`.
@@ -193,7 +202,7 @@ function refFromScriptRef(scriptRef) {
193
202
*
194
203
* @returns {string|undefined } the ref embedded within `scriptRef`
195
204
*/
196
- function ifaceFromScriptRef ( scriptRef ) {
205
+ function ifaceOf ( scriptRef ) {
197
206
const delim = scriptRef . indexOf ( ':' ) ;
198
207
if ( delim < 0 ) {
199
208
return undefined ;
@@ -227,13 +236,13 @@ function capdata(from) {
227
236
}
228
237
case 'string' :
229
238
if ( value [ 0 ] === '@' ) {
230
- const ref = refFromScriptRef ( value ) ;
239
+ const ref = refOf ( value ) ;
231
240
let index = slots . findIndex ( x => x === ref ) ;
232
241
if ( index < 0 ) {
233
242
index = slots . length ;
234
243
slots . push ( ref ) ;
235
244
}
236
- const iface = ifaceFromScriptRef ( value ) ;
245
+ const iface = ifaceOf ( value ) ;
237
246
return { [ QCLASS ] : 'slot' , iface, index } ;
238
247
} else {
239
248
return value ;
@@ -330,6 +339,7 @@ export function commsVatDriver(t, verbose = false) {
330
339
const log = [ ] ;
331
340
const syscall = loggingSyscall ( log ) ;
332
341
const d = buildCommsDispatch ( syscall , 'fakestate' , 'fakehelpers' ) ;
342
+ const { state } = debugState . get ( d ) ;
333
343
334
344
const remotes = new Map ( ) ;
335
345
@@ -534,8 +544,8 @@ export function commsVatDriver(t, verbose = false) {
534
544
*/
535
545
function makeNewRemote ( name , transmitter , receiver ) {
536
546
remotes . set ( name , {
537
- transmitter : refFromScriptRef ( transmitter ) ,
538
- receiver : refFromScriptRef ( receiver ) ,
547
+ transmitter : refOf ( transmitter ) ,
548
+ receiver : refOf ( receiver ) ,
539
549
sendToSeqNum : 1 ,
540
550
sendFromSeqNum : 1 ,
541
551
lastToSeqNum : 0 ,
@@ -619,7 +629,7 @@ export function commsVatDriver(t, verbose = false) {
619
629
}
620
630
}
621
631
622
- const exportObjectCounter = { k : 30 , a : 20 , b : 20 , c : 20 } ;
632
+ const exportObjectCounter = { k : 30 , a : 20 , b : 1020 , c : 2020 } ;
623
633
/**
624
634
* Allocate a new scriptref for an exported object.
625
635
*
@@ -657,14 +667,15 @@ export function commsVatDriver(t, verbose = false) {
657
667
}
658
668
const [ who , dir , op ] = what ;
659
669
insistProperActor ( who ) ;
660
- assert ( dir === '>' || dir === '<' ) ;
670
+ assert ( dir === '>' || dir === '<' || dir === ':' ) ;
661
671
assert ( op === 'm' || op === 'r' || op === 's' || op === 'l' ) ;
662
672
663
673
switch ( op ) {
664
674
case 'm' : {
665
- const target = refFromScriptRef ( params [ 0 ] ) ;
675
+ assert ( dir === '<' || dir === '>' ) ;
676
+ const target = refOf ( params [ 0 ] ) ;
666
677
const method = params [ 1 ] ;
667
- const result = params [ 2 ] ? refFromScriptRef ( params [ 2 ] ) : undefined ;
678
+ const result = params [ 2 ] ? refOf ( params [ 2 ] ) : undefined ;
668
679
const args = capdata ( params . slice ( 3 ) ) ;
669
680
if ( dir === '>' ) {
670
681
injectSend ( who , target , method , args , result ) ;
@@ -674,9 +685,10 @@ export function commsVatDriver(t, verbose = false) {
674
685
break ;
675
686
}
676
687
case 'r' : {
688
+ assert ( dir === '<' || dir === '>' ) ;
677
689
const resolutions = [ ] ;
678
690
for ( const resolution of params ) {
679
- const target = refFromScriptRef ( resolution [ 0 ] ) ;
691
+ const target = refOf ( resolution [ 0 ] ) ;
680
692
const status = resolution [ 1 ] ;
681
693
const value = capdata ( resolution [ 2 ] ) ;
682
694
resolutions . push ( [ target , status , value ] ) ;
@@ -691,13 +703,13 @@ export function commsVatDriver(t, verbose = false) {
691
703
case 's' : {
692
704
// The 's' (subscribe) op is only allowed as a kernal observation
693
705
assert ( who === 'k' && dir === '<' ) ;
694
- const target = refFromScriptRef ( params [ 0 ] ) ;
706
+ const target = refOf ( params [ 0 ] ) ;
695
707
observeSubscribe ( target ) ;
696
708
break ;
697
709
}
698
710
case 'l' : {
699
- // The 'l' (lag) op is only allowed as a remote injection
700
- assert ( who !== 'k' && dir === '> ' ) ;
711
+ // The 'l' (lag) op is only allowed as a control operation
712
+ assert ( who !== 'k' && dir === ': ' ) ;
701
713
injectLag ( who , params [ 0 ] ) ;
702
714
break ;
703
715
}
@@ -769,6 +781,7 @@ export function commsVatDriver(t, verbose = false) {
769
781
770
782
return {
771
783
_,
784
+ state,
772
785
done,
773
786
setupRemote,
774
787
importFromRemote,
@@ -777,5 +790,7 @@ export function commsVatDriver(t, verbose = false) {
777
790
newExportObject,
778
791
newImportPromise,
779
792
newExportPromise,
793
+ refOf,
794
+ flipRefOf,
780
795
} ;
781
796
}
0 commit comments