@@ -370,6 +370,10 @@ extension Instruction.Payload {
370370 }
371371}
372372
373+ // TODO: Consider switching all quantification to a quantification
374+ // instruction, where the general path has an instruction list (i.e. a
375+ // slice of a list)
376+
373377// MARK: Struct definitions
374378struct QuantifyPayload : RawRepresentable {
375379 let rawValue : UInt64
@@ -380,9 +384,12 @@ struct QuantifyPayload: RawRepresentable {
380384 case builtin = 4
381385 }
382386
387+ // TODO: figure out how to better organize this...
388+
383389 // Future work: optimize this layout -> payload type should be a fast switch
384390 // The top 8 bits are reserved for the opcode so we have 56 bits to work with
385- // b55-b38 - Unused
391+ // b55-b39 - Unused
392+ // b39-b38 - isScalarSemantics
386393 // b38-b35 - Payload type (one of 4 types, stored on 3 bits)
387394 // b35-b27 - minTrips (8 bit int)
388395 // b27-b18 - extraTrips (8 bit value, one bit for nil)
@@ -393,6 +400,7 @@ struct QuantifyPayload: RawRepresentable {
393400 static var minTripsShift : UInt64 { 27 }
394401 static var typeShift : UInt64 { 35 }
395402 static var maxStorableTrips : UInt64 { ( 1 << 8 ) - 1 }
403+ static var isScalarSemanticsBit : UInt64 { 1 &<< 38 }
396404
397405 var quantKindMask : UInt64 { 3 }
398406 var extraTripsMask : UInt64 { 0x1FF }
@@ -404,7 +412,8 @@ struct QuantifyPayload: RawRepresentable {
404412 _ kind: AST . Quantification . Kind ,
405413 _ minTrips: Int ,
406414 _ extraTrips: Int ? ,
407- _ type: PayloadType
415+ _ type: PayloadType ,
416+ isScalarSemantics: Bool
408417 ) -> UInt64 {
409418 let kindVal : UInt64
410419 switch kind {
@@ -415,11 +424,14 @@ struct QuantifyPayload: RawRepresentable {
415424 case . possessive:
416425 kindVal = 2
417426 }
427+ // TODO: refactor / reimplement
418428 let extraTripsVal : UInt64 = extraTrips == nil ? 1 : UInt64 ( extraTrips!) << 1
419- return ( kindVal << QuantifyPayload . quantKindShift) +
420- ( extraTripsVal << QuantifyPayload . extraTripsShift) +
421- ( UInt64 ( minTrips) << QuantifyPayload . minTripsShift) +
422- ( type. rawValue << QuantifyPayload . typeShift)
429+ let scalarSemanticsBit = isScalarSemantics ? Self . isScalarSemanticsBit : 0
430+ return ( kindVal << QuantifyPayload . quantKindShift) |
431+ ( extraTripsVal << QuantifyPayload . extraTripsShift) |
432+ ( UInt64 ( minTrips) << QuantifyPayload . minTripsShift) |
433+ ( type. rawValue << QuantifyPayload . typeShift) |
434+ scalarSemanticsBit
423435 }
424436
425437 init ( rawValue: UInt64 ) {
@@ -431,46 +443,49 @@ struct QuantifyPayload: RawRepresentable {
431443 bitset: AsciiBitsetRegister ,
432444 _ kind: AST . Quantification . Kind ,
433445 _ minTrips: Int ,
434- _ extraTrips: Int ?
446+ _ extraTrips: Int ? ,
447+ isScalarSemantics: Bool
435448 ) {
436449 assert ( bitset. bits <= _payloadMask)
437450 self . rawValue = bitset. bits
438- + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . bitset)
451+ + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . bitset, isScalarSemantics : isScalarSemantics )
439452 }
440453
441454 init (
442455 asciiChar: UInt8 ,
443456 _ kind: AST . Quantification . Kind ,
444457 _ minTrips: Int ,
445- _ extraTrips: Int ?
458+ _ extraTrips: Int ? ,
459+ isScalarSemantics: Bool
446460 ) {
447461 self . rawValue = UInt64 ( asciiChar)
448- + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . asciiChar)
462+ + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . asciiChar, isScalarSemantics : isScalarSemantics )
449463 }
450464
451465 init (
452466 matchesNewlines: Bool ,
453467 _ kind: AST . Quantification . Kind ,
454468 _ minTrips: Int ,
455- _ extraTrips: Int ?
469+ _ extraTrips: Int ? ,
470+ isScalarSemantics: Bool
456471 ) {
457472 self . rawValue = ( matchesNewlines ? 1 : 0 )
458- + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . any)
473+ + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . any, isScalarSemantics : isScalarSemantics )
459474 }
460475
461476 init (
462477 model: _CharacterClassModel ,
463478 _ kind: AST . Quantification . Kind ,
464479 _ minTrips: Int ,
465- _ extraTrips: Int ?
480+ _ extraTrips: Int ? ,
481+ isScalarSemantics: Bool
466482 ) {
467483 assert ( model. cc. rawValue < 0xFF )
468- assert ( model. matchLevel != . unicodeScalar)
469484 let packedModel = model. cc. rawValue
470485 + ( model. isInverted ? 1 << 9 : 0 )
471486 + ( model. isStrictASCII ? 1 << 10 : 0 )
472487 self . rawValue = packedModel
473- + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . builtin)
488+ + QuantifyPayload. packInfoValues ( kind, minTrips, extraTrips, . builtin, isScalarSemantics : isScalarSemantics )
474489 }
475490
476491 var type : PayloadType {
@@ -500,6 +515,10 @@ struct QuantifyPayload: RawRepresentable {
500515 }
501516 }
502517
518+ var isScalarSemantics : Bool {
519+ rawValue & Self . isScalarSemanticsBit != 0
520+ }
521+
503522 var bitset : AsciiBitsetRegister {
504523 TypedInt ( self . rawValue & payloadMask)
505524 }
0 commit comments