10812 lines
436 KiB
Rust
10812 lines
436 KiB
Rust
use std::{
|
|
ffi::OsStr,
|
|
fs,
|
|
path::{Path, PathBuf},
|
|
process::{Command, Output},
|
|
};
|
|
|
|
const DIAGNOSTIC_SNAPSHOTS: &[&str] = &[
|
|
"array-index-out-of-bounds.diag",
|
|
"array-index-not-i32.diag",
|
|
"array-argument-type-mismatch.diag",
|
|
"array-local-initializer-type-mismatch.diag",
|
|
"array-return-type-mismatch.diag",
|
|
"arity-mismatch.diag",
|
|
"cyclic-struct-fields.diag",
|
|
"cyclic-type-alias.diag",
|
|
"duplicate-local.diag",
|
|
"duplicate-match-arm.diag",
|
|
"duplicate-struct-constructor-field.diag",
|
|
"duplicate-struct-field.diag",
|
|
"duplicate-struct.diag",
|
|
"duplicate-type-alias.diag",
|
|
"empty-array.diag",
|
|
"enum-constructor-arity.diag",
|
|
"enum-container-values.diag",
|
|
"enum-duplicate-variant.diag",
|
|
"enum-duplicate.diag",
|
|
"enum-empty.diag",
|
|
"enum-match-duplicate-arm.diag",
|
|
"enum-match-invalid-arm.diag",
|
|
"enum-match-non-exhaustive.diag",
|
|
"enum-match-payload-binding.diag",
|
|
"enum-ordering.diag",
|
|
"enum-payload-constructor-arity.diag",
|
|
"enum-payload-constructor-type.diag",
|
|
"enum-payload-recursive-struct.diag",
|
|
"enum-payload-struct-equality.diag",
|
|
"enum-payload-mixed-types.diag",
|
|
"enum-payload-match-missing-binding.diag",
|
|
"enum-payload-unsupported-type.diag",
|
|
"enum-printing.diag",
|
|
"enum-subject-mismatch.diag",
|
|
"enum-struct-fields-container.diag",
|
|
"enum-unknown-constructor.diag",
|
|
"enum-unknown-variant.diag",
|
|
"enum-unqualified-variant-constructor.diag",
|
|
"if-branch-type-mismatch.diag",
|
|
"if-condition-not-bool.diag",
|
|
"i64-literal-out-of-range.diag",
|
|
"index-on-non-array.diag",
|
|
"integer-out-of-range.diag",
|
|
"invalid-i64-literal.diag",
|
|
"invalid-leading-plus-i64-literal.diag",
|
|
"invalid-sign-only-i64-literal.diag",
|
|
"empty-struct.diag",
|
|
"empty-while-body.diag",
|
|
"local-redeclares-parameter.diag",
|
|
"local-shadows-function.diag",
|
|
"local-shadows-intrinsic.diag",
|
|
"match-arm-type-mismatch.diag",
|
|
"match-binding-collision.diag",
|
|
"match-subject-type-mismatch.diag",
|
|
"malformed-option-unwrap.diag",
|
|
"malformed-option-constructor.diag",
|
|
"malformed-if.diag",
|
|
"malformed-match-pattern.diag",
|
|
"malformed-result-err-unwrap.diag",
|
|
"malformed-result-ok-unwrap.diag",
|
|
"malformed-result-constructor.diag",
|
|
"malformed-type-alias.diag",
|
|
"malformed-unsafe-form.diag",
|
|
"malformed-while.diag",
|
|
"field-access-on-non-struct.diag",
|
|
"recursive-struct-field.diag",
|
|
"nested-local-declaration.diag",
|
|
"nested-while.diag",
|
|
"non-exhaustive-match.diag",
|
|
"option-constructor-type-mismatch.diag",
|
|
"option-unwrap-non-option.diag",
|
|
"print-bool-arity.diag",
|
|
"print-bool-type.diag",
|
|
"result-constructor-type-mismatch.diag",
|
|
"result-err-unwrap-non-result.diag",
|
|
"result-ok-unwrap-non-result.diag",
|
|
"set-immutable-local.diag",
|
|
"set-parameter.diag",
|
|
"single-file-main-i64-return.diag",
|
|
"self-type-alias.diag",
|
|
"set-type-mismatch.diag",
|
|
"set-unknown-local.diag",
|
|
"std-abi-layout-unsupported.diag",
|
|
"std-async-spawn-unsupported.diag",
|
|
"std-env-get-type.diag",
|
|
"std-env-get-result-type.diag",
|
|
"std-fs-read-binary-unsupported-alias.diag",
|
|
"std-fs-read-text-helper-shadow.diag",
|
|
"std-fs-list-dir-unsupported.diag",
|
|
"std-fs-write-text-arity.diag",
|
|
"std-fs-write-text-result-arity.diag",
|
|
"std-fs-write-text-result-type.diag",
|
|
"std-io-prompt-unsupported.diag",
|
|
"std-io-read-stdin-async-unsupported.diag",
|
|
"std-io-read-stdin-binary-unsupported.diag",
|
|
"std-io-read-stdin-bytes-unsupported.diag",
|
|
"std-io-read-stdin-result-arity.diag",
|
|
"std-io-read-stdin-result-bool-context.diag",
|
|
"std-io-read-stdin-result-helper-shadow.diag",
|
|
"std-io-read-stdin-result-name-shadow.diag",
|
|
"std-io-read-stdin-result-type.diag",
|
|
"std-io-read-line-unsupported.diag",
|
|
"std-io-read-stdin-unsupported.diag",
|
|
"std-io-stdin-encoding-unsupported.diag",
|
|
"std-io-stdin-lines-unsupported.diag",
|
|
"std-io-stdin-stream-unsupported.diag",
|
|
"std-io-eprint-arity.diag",
|
|
"std-io-eprint-result-context.diag",
|
|
"std-net-connect-unsupported.diag",
|
|
"std-num-cast-checked-unsupported.diag",
|
|
"std-num-cast-unsupported.diag",
|
|
"std-num-f64-to-i32-result-arity.diag",
|
|
"std-num-f64-to-i32-result-bool-context.diag",
|
|
"std-num-f64-to-i32-result-context.diag",
|
|
"std-num-f64-to-i32-result-name-shadow.diag",
|
|
"std-num-f64-to-i32-result-type.diag",
|
|
"std-num-f64-to-i32-unsupported.diag",
|
|
"std-num-f64-to-i64-result-arity.diag",
|
|
"std-num-f64-to-i64-result-bool-context.diag",
|
|
"std-num-f64-to-i64-result-context.diag",
|
|
"std-num-f64-to-i64-result-name-shadow.diag",
|
|
"std-num-f64-to-i64-result-type.diag",
|
|
"std-num-f64-to-i64-unsupported.diag",
|
|
"std-num-f64-to-string-arity.diag",
|
|
"std-num-f64-to-string-bool-context.diag",
|
|
"std-num-f64-to-string-context.diag",
|
|
"std-num-f64-to-string-helper-shadow.diag",
|
|
"std-num-f64-to-string-name-shadow.diag",
|
|
"std-num-f64-to-string-type.diag",
|
|
"std-num-i32-to-f64-type.diag",
|
|
"std-num-i32-to-i64-arity.diag",
|
|
"std-num-i32-to-i64-result-unsupported.diag",
|
|
"std-num-i32-to-string-arity.diag",
|
|
"std-num-i64-to-i32-result-arity.diag",
|
|
"std-num-i64-to-i32-result-type.diag",
|
|
"std-num-i64-to-i32-unsupported.diag",
|
|
"std-num-i64-to-string-type.diag",
|
|
"std-num-to-string-unsupported.diag",
|
|
"std-package-load-unsupported.diag",
|
|
"std-platform-os-unsupported.diag",
|
|
"std-print-bool-arity.diag",
|
|
"std-print-bool-result.diag",
|
|
"std-parameter-shadows-runtime.diag",
|
|
"std-process-arg-result-arity.diag",
|
|
"std-process-arg-result-helper-shadow.diag",
|
|
"std-process-arg-result-name-shadow.diag",
|
|
"std-process-arg-type.diag",
|
|
"std-random-bytes-unsupported.diag",
|
|
"std-random-crypto-i32-unsupported.diag",
|
|
"std-random-float-unsupported.diag",
|
|
"std-random-i32-arity.diag",
|
|
"std-random-i32-bool-context.diag",
|
|
"std-random-i32-helper-shadow.diag",
|
|
"std-random-i32-name-shadow.diag",
|
|
"std-random-range-unsupported.diag",
|
|
"std-random-seed-unsupported.diag",
|
|
"std-random-shuffle-unsupported.diag",
|
|
"std-random-string-unsupported.diag",
|
|
"std-random-uuid-unsupported.diag",
|
|
"std-result-map-unsupported.diag",
|
|
"std-vec-empty-generic-unsupported.diag",
|
|
"std-string-byte-at-result-arity.diag",
|
|
"std-string-byte-at-result-bool-context.diag",
|
|
"std-string-byte-at-result-context.diag",
|
|
"std-string-byte-at-result-helper-shadow.diag",
|
|
"std-string-byte-at-result-name-shadow.diag",
|
|
"std-string-byte-at-result-type.diag",
|
|
"std-string-byte-at-unsupported.diag",
|
|
"std-string-concat-arity.diag",
|
|
"std-string-concat-helper-shadow.diag",
|
|
"std-string-concat-result-context.diag",
|
|
"std-string-concat-type.diag",
|
|
"std-string-concat-unsupported-string-container.diag",
|
|
"std-string-contains-unsupported.diag",
|
|
"std-string-ends-with-arity.diag",
|
|
"std-string-ends-with-context.diag",
|
|
"std-string-ends-with-helper-shadow.diag",
|
|
"std-string-ends-with-name-shadow.diag",
|
|
"std-string-ends-with-type.diag",
|
|
"std-string-find-result-unsupported.diag",
|
|
"std-string-from-i64-unsupported.diag",
|
|
"std-string-index-unsupported.diag",
|
|
"std-string-len-type.diag",
|
|
"std-string-parse-bool-unsupported.diag",
|
|
"std-string-parse-bool-result-arity.diag",
|
|
"std-string-parse-bool-result-bool-context.diag",
|
|
"std-string-parse-bool-result-context.diag",
|
|
"std-string-parse-bool-result-helper-shadow.diag",
|
|
"std-string-parse-bool-result-name-shadow.diag",
|
|
"std-string-parse-bool-result-type.diag",
|
|
"std-string-parse-bytes-unsupported.diag",
|
|
"std-string-parse-f64-unsupported.diag",
|
|
"std-string-parse-generic-unsupported.diag",
|
|
"std-string-parse-i32-base-prefix-unsupported.diag",
|
|
"std-string-parse-i32-binary-unsupported.diag",
|
|
"std-string-parse-i32-code-unsupported.diag",
|
|
"std-string-parse-i32-error-adt-unsupported.diag",
|
|
"std-string-parse-i32-hex-unsupported.diag",
|
|
"std-string-parse-i32-locale-unsupported.diag",
|
|
"std-string-parse-i32-message-unsupported.diag",
|
|
"std-string-parse-i32-octal-unsupported.diag",
|
|
"std-string-parse-i32-plus-unsupported.diag",
|
|
"std-string-parse-i32-radix-unsupported.diag",
|
|
"std-string-parse-i32-result-arity.diag",
|
|
"std-string-parse-i32-result-bool-context.diag",
|
|
"std-string-parse-i32-result-context.diag",
|
|
"std-string-parse-i32-result-helper-shadow.diag",
|
|
"std-string-parse-i32-result-name-shadow.diag",
|
|
"std-string-parse-i32-result-type.diag",
|
|
"std-string-parse-i64-result-arity.diag",
|
|
"std-string-parse-i64-result-bool-context.diag",
|
|
"std-string-parse-i64-result-context.diag",
|
|
"std-string-parse-i64-result-helper-shadow.diag",
|
|
"std-string-parse-i64-result-name-shadow.diag",
|
|
"std-string-parse-i64-result-type.diag",
|
|
"std-string-parse-f64-result-arity.diag",
|
|
"std-string-parse-f64-result-bool-context.diag",
|
|
"std-string-parse-f64-result-context.diag",
|
|
"std-string-parse-f64-result-helper-shadow.diag",
|
|
"std-string-parse-f64-result-name-shadow.diag",
|
|
"std-string-parse-f64-result-type.diag",
|
|
"std-string-parse-i32-trim-unsupported.diag",
|
|
"std-string-parse-i32-underscore-unsupported.diag",
|
|
"std-string-parse-i32-unicode-unsupported.diag",
|
|
"std-string-parse-i32-unsupported.diag",
|
|
"std-string-parse-i32-whitespace-unsupported.diag",
|
|
"std-string-parse-string-unsupported.diag",
|
|
"std-string-scan-unsupported.diag",
|
|
"std-string-slice-result-arity.diag",
|
|
"std-string-slice-result-bool-context.diag",
|
|
"std-string-slice-result-context.diag",
|
|
"std-string-slice-result-helper-shadow.diag",
|
|
"std-string-slice-result-name-shadow.diag",
|
|
"std-string-slice-result-type.diag",
|
|
"std-string-slice-unsupported.diag",
|
|
"std-string-split-unsupported.diag",
|
|
"std-string-starts-with-arity.diag",
|
|
"std-string-starts-with-context.diag",
|
|
"std-string-starts-with-helper-shadow.diag",
|
|
"std-string-starts-with-name-shadow.diag",
|
|
"std-string-starts-with-type.diag",
|
|
"std-string-tokenize-unsupported.diag",
|
|
"std-terminal-clear-unsupported.diag",
|
|
"std-terminal-echo-unsupported.diag",
|
|
"std-terminal-is-tty-unsupported.diag",
|
|
"std-terminal-raw-mode-unsupported.diag",
|
|
"std-time-monotonic-arity.diag",
|
|
"std-time-monotonic-helper-shadow.diag",
|
|
"std-time-monotonic-name-shadow.diag",
|
|
"std-time-monotonic-result-context.diag",
|
|
"std-time-now-unsupported.diag",
|
|
"std-time-sleep-arity.diag",
|
|
"std-time-sleep-helper-shadow.diag",
|
|
"std-time-sleep-name-shadow.diag",
|
|
"std-time-sleep-type.diag",
|
|
"std-vec-i32-append-vector-type.diag",
|
|
"std-vec-i32-arity.diag",
|
|
"std-vec-i32-empty-arity.diag",
|
|
"std-vec-i32-helper-shadow.diag",
|
|
"std-vec-i32-index-arity.diag",
|
|
"std-vec-i32-index-index-type.diag",
|
|
"std-vec-i32-index-vector-type.diag",
|
|
"std-vec-i32-len-arity.diag",
|
|
"std-vec-i32-len-type.diag",
|
|
"std-vec-i32-one-sided-equality.diag",
|
|
"std-vec-i32-push-alias.diag",
|
|
"std-vec-i32-result-context.diag",
|
|
"std-vec-i32-type.diag",
|
|
"std-vec-i64-append-vector-type.diag",
|
|
"std-vec-i64-arity.diag",
|
|
"std-vec-i64-empty-arity.diag",
|
|
"std-vec-i64-helper-shadow.diag",
|
|
"std-vec-i64-index-arity.diag",
|
|
"std-vec-i64-index-index-type.diag",
|
|
"std-vec-i64-index-vector-type.diag",
|
|
"std-vec-i64-len-arity.diag",
|
|
"std-vec-i64-len-type.diag",
|
|
"std-vec-i64-one-sided-equality.diag",
|
|
"std-vec-i64-push-alias.diag",
|
|
"std-vec-i64-result-context.diag",
|
|
"std-vec-i64-type.diag",
|
|
"std-vec-string-append-vector-type.diag",
|
|
"std-vec-string-arity.diag",
|
|
"std-vec-string-empty-arity.diag",
|
|
"std-vec-string-helper-shadow.diag",
|
|
"std-vec-string-index-arity.diag",
|
|
"std-vec-string-index-index-type.diag",
|
|
"std-vec-string-index-vector-type.diag",
|
|
"std-vec-string-len-arity.diag",
|
|
"std-vec-string-len-type.diag",
|
|
"std-vec-string-one-sided-equality.diag",
|
|
"std-vec-string-push-alias.diag",
|
|
"std-vec-string-result-context.diag",
|
|
"std-vec-string-type.diag",
|
|
"string-len-arity.diag",
|
|
"string-len-type.diag",
|
|
"struct-field-order-mismatch.diag",
|
|
"struct-missing-field.diag",
|
|
"struct-unknown-field.diag",
|
|
"test-duplicate-name.diag",
|
|
"test-invalid-escaped-name.diag",
|
|
"test-invalid-form.diag",
|
|
"test-invalid-name.diag",
|
|
"test-non-bool.diag",
|
|
"type-mismatch.diag",
|
|
"type-alias-name-conflict.diag",
|
|
"type-alias-value-name-conflict.diag",
|
|
"unclosed-list.diag",
|
|
"unknown-type-alias-target.diag",
|
|
"unsupported-type-alias-target.diag",
|
|
"unknown-function.diag",
|
|
"unknown-struct-local.diag",
|
|
"unknown-struct-parameter.diag",
|
|
"unknown-struct-return.diag",
|
|
"unknown-top-level-form.diag",
|
|
"unsafe-parameter-shadows-callable.diag",
|
|
"unsafe-required-dealloc.diag",
|
|
"unsafe-required-ffi-call.diag",
|
|
"unsafe-required-load.diag",
|
|
"unsafe-required-operation.diag",
|
|
"unsafe-required-ptr-add.diag",
|
|
"unsafe-required-reinterpret.diag",
|
|
"unsafe-required-store.diag",
|
|
"unsafe-required-unchecked-index.diag",
|
|
"unsupported-local-type.diag",
|
|
"unsupported-match-container.diag",
|
|
"unsupported-match-mutation.diag",
|
|
"unsupported-match-payload-type.diag",
|
|
"unsupported-standard-library-call.diag",
|
|
"unsupported-option-result-equality.diag",
|
|
"unsupported-result-string-equality.diag",
|
|
"option-observation-non-option.diag",
|
|
"unsupported-option-result-print.diag",
|
|
"unsupported-result-string-print.diag",
|
|
"unsupported-option-parameter-payload-type.diag",
|
|
"result-observation-non-result.diag",
|
|
"unsupported-option-return-payload-type.diag",
|
|
"unsupported-option-payload-type.diag",
|
|
"unsupported-primitive-struct-field-container.diag",
|
|
"unsupported-array-element-type.diag",
|
|
"unsupported-array-equality.diag",
|
|
"unsupported-array-local-mutation.diag",
|
|
"unsupported-array-print.diag",
|
|
"unsupported-array-signature-element-type.diag",
|
|
"unsupported-float-literal.diag",
|
|
"unsupported-generic-function.diag",
|
|
"unsupported-generic-type-alias.diag",
|
|
"unsupported-generic-type-parameter.diag",
|
|
"unsupported-generic-vec-type.diag",
|
|
"unsupported-map-type.diag",
|
|
"unsupported-signature-type.diag",
|
|
"unsupported-set-type.diag",
|
|
"unsupported-result-parameter-payload-type.diag",
|
|
"unsupported-result-return-payload-type.diag",
|
|
"unsupported-unit-parameter-signature.diag",
|
|
"unsupported-unit-return-signature.diag",
|
|
"unsupported-result-payload-type.diag",
|
|
"unsupported-result-string-bool.diag",
|
|
"unsupported-struct-field-type.diag",
|
|
"unsupported-struct-field-mutation.diag",
|
|
"unsupported-print-unit.diag",
|
|
"unsupported-string-array.diag",
|
|
"unsupported-string-concatenation.diag",
|
|
"unsupported-string-escape.diag",
|
|
"unsupported-string-literal.diag",
|
|
"unsupported-vec-element-type.diag",
|
|
"unsupported-vec-literal.diag",
|
|
"unsupported-vec-nesting.diag",
|
|
"unsupported-vec-option.diag",
|
|
"unsupported-vec-result.diag",
|
|
"unsupported-unsafe-dealloc.diag",
|
|
"unsupported-unsafe-ffi-call.diag",
|
|
"unsupported-unsafe-load.diag",
|
|
"unsupported-unsafe-operation.diag",
|
|
"unsupported-unsafe-ptr-add.diag",
|
|
"unsupported-unsafe-reinterpret.diag",
|
|
"unsupported-unsafe-store.diag",
|
|
"unsupported-unsafe-unchecked-index.diag",
|
|
"while-body-local.diag",
|
|
"while-body-non-unit.diag",
|
|
"while-condition-not-bool.diag",
|
|
"while-final-function.diag",
|
|
"while-final-test.diag",
|
|
"zero-length-array-type.diag",
|
|
];
|
|
|
|
const LOWERING_INSPECTOR_FIXTURES: &[&str] = &[
|
|
"add.checked.lower",
|
|
"add.surface.lower",
|
|
"array-direct-scalars-value-flow.checked.lower",
|
|
"array-direct-scalars-value-flow.surface.lower",
|
|
"array-direct-scalars.checked.lower",
|
|
"array-direct-scalars.surface.lower",
|
|
"array-enum.checked.lower",
|
|
"array-enum.surface.lower",
|
|
"array-string-value-flow.checked.lower",
|
|
"array-string-value-flow.surface.lower",
|
|
"array-string.checked.lower",
|
|
"array-string.surface.lower",
|
|
"array-struct-elements.checked.lower",
|
|
"array-struct-elements.surface.lower",
|
|
"array-struct-fields.checked.lower",
|
|
"array-struct-fields.surface.lower",
|
|
"array-value-flow.checked.lower",
|
|
"array-value-flow.surface.lower",
|
|
"array.checked.lower",
|
|
"array.surface.lower",
|
|
"checked-i64-to-i32-conversion.checked.lower",
|
|
"checked-i64-to-i32-conversion.surface.lower",
|
|
"comments.checked.lower",
|
|
"comments.surface.lower",
|
|
"enum-basic.checked.lower",
|
|
"enum-basic.surface.lower",
|
|
"enum-payload-direct-scalars.checked.lower",
|
|
"enum-payload-direct-scalars.surface.lower",
|
|
"enum-payload-structs.checked.lower",
|
|
"enum-payload-structs.surface.lower",
|
|
"enum-payload-i32.checked.lower",
|
|
"enum-payload-i32.surface.lower",
|
|
"enum-struct-fields.checked.lower",
|
|
"enum-struct-fields.surface.lower",
|
|
"f64-numeric-primitive.checked.lower",
|
|
"f64-numeric-primitive.surface.lower",
|
|
"f64-to-i32-result.checked.lower",
|
|
"f64-to-i32-result.surface.lower",
|
|
"f64-to-i64-result.checked.lower",
|
|
"f64-to-i64-result.surface.lower",
|
|
"i64-numeric-primitive.checked.lower",
|
|
"i64-numeric-primitive.surface.lower",
|
|
"numeric-widening-conversions.checked.lower",
|
|
"numeric-widening-conversions.surface.lower",
|
|
"numeric-struct-fields.checked.lower",
|
|
"numeric-struct-fields.surface.lower",
|
|
"formatter-stability-v1.checked.lower",
|
|
"formatter-stability-v1.surface.lower",
|
|
"host-io.checked.lower",
|
|
"host-io-result.checked.lower",
|
|
"host-io-result.surface.lower",
|
|
"host-io.surface.lower",
|
|
"if.checked.lower",
|
|
"if.surface.lower",
|
|
"f64-to-string.checked.lower",
|
|
"f64-to-string.surface.lower",
|
|
"integer-to-string.checked.lower",
|
|
"integer-to-string.surface.lower",
|
|
"composite-locals.checked.lower",
|
|
"composite-locals.surface.lower",
|
|
"composite-struct-fields.checked.lower",
|
|
"composite-struct-fields.surface.lower",
|
|
"local-variables.checked.lower",
|
|
"local-variables.surface.lower",
|
|
"option-result-flow.checked.lower",
|
|
"option-result-flow.surface.lower",
|
|
"option-result-match.checked.lower",
|
|
"option-result-match.surface.lower",
|
|
"option-result-payload.checked.lower",
|
|
"option-result-payload.surface.lower",
|
|
"option-result.checked.lower",
|
|
"option-result.surface.lower",
|
|
"owned-string-concat.checked.lower",
|
|
"owned-string-concat.surface.lower",
|
|
"print-bool.checked.lower",
|
|
"print-bool.surface.lower",
|
|
"primitive-struct-fields.checked.lower",
|
|
"primitive-struct-fields.surface.lower",
|
|
"random.checked.lower",
|
|
"random.surface.lower",
|
|
"result-helpers.checked.lower",
|
|
"result-helpers.surface.lower",
|
|
"string-print.checked.lower",
|
|
"string-print.surface.lower",
|
|
"standard-runtime.checked.lower",
|
|
"standard-runtime.surface.lower",
|
|
"standard-io-host-env.checked.lower",
|
|
"standard-io-host-env.surface.lower",
|
|
"stdin-result.checked.lower",
|
|
"stdin-result.surface.lower",
|
|
"string-parse-i32-result.checked.lower",
|
|
"string-parse-i32-result.surface.lower",
|
|
"string-parse-i64-result.checked.lower",
|
|
"string-parse-i64-result.surface.lower",
|
|
"string-parse-u32-result.checked.lower",
|
|
"string-parse-u32-result.surface.lower",
|
|
"string-parse-u64-result.checked.lower",
|
|
"string-parse-u64-result.surface.lower",
|
|
"string-parse-f64-result.checked.lower",
|
|
"string-parse-f64-result.surface.lower",
|
|
"string-parse-bool-result.checked.lower",
|
|
"string-parse-bool-result.surface.lower",
|
|
"string-value-flow.checked.lower",
|
|
"string-value-flow.surface.lower",
|
|
"struct-value-flow.checked.lower",
|
|
"struct-value-flow.surface.lower",
|
|
"struct.checked.lower",
|
|
"struct.surface.lower",
|
|
"time-sleep.checked.lower",
|
|
"time-sleep.surface.lower",
|
|
"top-level-test.checked.lower",
|
|
"top-level-test.surface.lower",
|
|
"type-aliases.checked.lower",
|
|
"type-aliases.surface.lower",
|
|
"u32-numeric-primitive.checked.lower",
|
|
"u32-numeric-primitive.surface.lower",
|
|
"u64-numeric-primitive.checked.lower",
|
|
"u64-numeric-primitive.surface.lower",
|
|
"unsafe.checked.lower",
|
|
"unsafe.surface.lower",
|
|
"unsigned-integer-to-string.checked.lower",
|
|
"unsigned-integer-to-string.surface.lower",
|
|
"vec-i32.checked.lower",
|
|
"vec-i32.surface.lower",
|
|
"while.checked.lower",
|
|
"while.surface.lower",
|
|
];
|
|
|
|
const LOWERING_INSPECTOR_CASES: &[LoweringInspectorCase] = &[
|
|
LoweringInspectorCase {
|
|
source: "examples/add.slo",
|
|
surface_snapshot: "add.surface.lower",
|
|
checked_snapshot: "add.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/top-level-test.slo",
|
|
surface_snapshot: "top-level-test.surface.lower",
|
|
checked_snapshot: "top-level-test.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/type-aliases.slo",
|
|
surface_snapshot: "type-aliases.surface.lower",
|
|
checked_snapshot: "type-aliases.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/comments.slo",
|
|
surface_snapshot: "comments.surface.lower",
|
|
checked_snapshot: "comments.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/enum-basic.slo",
|
|
surface_snapshot: "enum-basic.surface.lower",
|
|
checked_snapshot: "enum-basic.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/enum-payload-i32.slo",
|
|
surface_snapshot: "enum-payload-i32.surface.lower",
|
|
checked_snapshot: "enum-payload-i32.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/enum-payload-direct-scalars.slo",
|
|
surface_snapshot: "enum-payload-direct-scalars.surface.lower",
|
|
checked_snapshot: "enum-payload-direct-scalars.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/enum-payload-structs.slo",
|
|
surface_snapshot: "enum-payload-structs.surface.lower",
|
|
checked_snapshot: "enum-payload-structs.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/enum-struct-fields.slo",
|
|
surface_snapshot: "enum-struct-fields.surface.lower",
|
|
checked_snapshot: "enum-struct-fields.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/primitive-struct-fields.slo",
|
|
surface_snapshot: "primitive-struct-fields.surface.lower",
|
|
checked_snapshot: "primitive-struct-fields.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/f64-numeric-primitive.slo",
|
|
surface_snapshot: "f64-numeric-primitive.surface.lower",
|
|
checked_snapshot: "f64-numeric-primitive.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/i64-numeric-primitive.slo",
|
|
surface_snapshot: "i64-numeric-primitive.surface.lower",
|
|
checked_snapshot: "i64-numeric-primitive.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/u32-numeric-primitive.slo",
|
|
surface_snapshot: "u32-numeric-primitive.surface.lower",
|
|
checked_snapshot: "u32-numeric-primitive.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/u64-numeric-primitive.slo",
|
|
surface_snapshot: "u64-numeric-primitive.surface.lower",
|
|
checked_snapshot: "u64-numeric-primitive.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/integer-to-string.slo",
|
|
surface_snapshot: "integer-to-string.surface.lower",
|
|
checked_snapshot: "integer-to-string.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/unsigned-integer-to-string.slo",
|
|
surface_snapshot: "unsigned-integer-to-string.surface.lower",
|
|
checked_snapshot: "unsigned-integer-to-string.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/f64-to-string.slo",
|
|
surface_snapshot: "f64-to-string.surface.lower",
|
|
checked_snapshot: "f64-to-string.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/f64-to-i32-result.slo",
|
|
surface_snapshot: "f64-to-i32-result.surface.lower",
|
|
checked_snapshot: "f64-to-i32-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/f64-to-i64-result.slo",
|
|
surface_snapshot: "f64-to-i64-result.surface.lower",
|
|
checked_snapshot: "f64-to-i64-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/numeric-widening-conversions.slo",
|
|
surface_snapshot: "numeric-widening-conversions.surface.lower",
|
|
checked_snapshot: "numeric-widening-conversions.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/numeric-struct-fields.slo",
|
|
surface_snapshot: "numeric-struct-fields.surface.lower",
|
|
checked_snapshot: "numeric-struct-fields.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/checked-i64-to-i32-conversion.slo",
|
|
surface_snapshot: "checked-i64-to-i32-conversion.surface.lower",
|
|
checked_snapshot: "checked-i64-to-i32-conversion.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/formatter-stability-v1.fmt",
|
|
surface_snapshot: "formatter-stability-v1.surface.lower",
|
|
checked_snapshot: "formatter-stability-v1.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/host-io.slo",
|
|
surface_snapshot: "host-io.surface.lower",
|
|
checked_snapshot: "host-io.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/host-io-result.slo",
|
|
surface_snapshot: "host-io-result.surface.lower",
|
|
checked_snapshot: "host-io-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/unsafe.slo",
|
|
surface_snapshot: "unsafe.surface.lower",
|
|
checked_snapshot: "unsafe.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/local-variables.slo",
|
|
surface_snapshot: "local-variables.surface.lower",
|
|
checked_snapshot: "local-variables.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/composite-locals.slo",
|
|
surface_snapshot: "composite-locals.surface.lower",
|
|
checked_snapshot: "composite-locals.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/composite-struct-fields.slo",
|
|
surface_snapshot: "composite-struct-fields.surface.lower",
|
|
checked_snapshot: "composite-struct-fields.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-struct-fields.slo",
|
|
surface_snapshot: "array-struct-fields.surface.lower",
|
|
checked_snapshot: "array-struct-fields.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/if.slo",
|
|
surface_snapshot: "if.surface.lower",
|
|
checked_snapshot: "if.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/while.slo",
|
|
surface_snapshot: "while.surface.lower",
|
|
checked_snapshot: "while.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/struct.slo",
|
|
surface_snapshot: "struct.surface.lower",
|
|
checked_snapshot: "struct.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/struct-value-flow.slo",
|
|
surface_snapshot: "struct-value-flow.surface.lower",
|
|
checked_snapshot: "struct-value-flow.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array.slo",
|
|
surface_snapshot: "array.surface.lower",
|
|
checked_snapshot: "array.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-direct-scalars.slo",
|
|
surface_snapshot: "array-direct-scalars.surface.lower",
|
|
checked_snapshot: "array-direct-scalars.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-direct-scalars-value-flow.slo",
|
|
surface_snapshot: "array-direct-scalars-value-flow.surface.lower",
|
|
checked_snapshot: "array-direct-scalars-value-flow.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-enum.slo",
|
|
surface_snapshot: "array-enum.surface.lower",
|
|
checked_snapshot: "array-enum.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-string.slo",
|
|
surface_snapshot: "array-string.surface.lower",
|
|
checked_snapshot: "array-string.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-string-value-flow.slo",
|
|
surface_snapshot: "array-string-value-flow.surface.lower",
|
|
checked_snapshot: "array-string-value-flow.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-value-flow.slo",
|
|
surface_snapshot: "array-value-flow.surface.lower",
|
|
checked_snapshot: "array-value-flow.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/array-struct-elements.slo",
|
|
surface_snapshot: "array-struct-elements.surface.lower",
|
|
checked_snapshot: "array-struct-elements.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/option-result.slo",
|
|
surface_snapshot: "option-result.surface.lower",
|
|
checked_snapshot: "option-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/option-result-flow.slo",
|
|
surface_snapshot: "option-result-flow.surface.lower",
|
|
checked_snapshot: "option-result-flow.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/option-result-match.slo",
|
|
surface_snapshot: "option-result-match.surface.lower",
|
|
checked_snapshot: "option-result-match.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/option-result-payload.slo",
|
|
surface_snapshot: "option-result-payload.surface.lower",
|
|
checked_snapshot: "option-result-payload.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-print.slo",
|
|
surface_snapshot: "string-print.surface.lower",
|
|
checked_snapshot: "string-print.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-value-flow.slo",
|
|
surface_snapshot: "string-value-flow.surface.lower",
|
|
checked_snapshot: "string-value-flow.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/print-bool.slo",
|
|
surface_snapshot: "print-bool.surface.lower",
|
|
checked_snapshot: "print-bool.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/random.slo",
|
|
surface_snapshot: "random.surface.lower",
|
|
checked_snapshot: "random.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/stdin-result.slo",
|
|
surface_snapshot: "stdin-result.surface.lower",
|
|
checked_snapshot: "stdin-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-parse-i32-result.slo",
|
|
surface_snapshot: "string-parse-i32-result.surface.lower",
|
|
checked_snapshot: "string-parse-i32-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-parse-i64-result.slo",
|
|
surface_snapshot: "string-parse-i64-result.surface.lower",
|
|
checked_snapshot: "string-parse-i64-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-parse-u32-result.slo",
|
|
surface_snapshot: "string-parse-u32-result.surface.lower",
|
|
checked_snapshot: "string-parse-u32-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-parse-u64-result.slo",
|
|
surface_snapshot: "string-parse-u64-result.surface.lower",
|
|
checked_snapshot: "string-parse-u64-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-parse-f64-result.slo",
|
|
surface_snapshot: "string-parse-f64-result.surface.lower",
|
|
checked_snapshot: "string-parse-f64-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/string-parse-bool-result.slo",
|
|
surface_snapshot: "string-parse-bool-result.surface.lower",
|
|
checked_snapshot: "string-parse-bool-result.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/result-helpers.slo",
|
|
surface_snapshot: "result-helpers.surface.lower",
|
|
checked_snapshot: "result-helpers.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/standard-runtime.slo",
|
|
surface_snapshot: "standard-runtime.surface.lower",
|
|
checked_snapshot: "standard-runtime.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/time-sleep.slo",
|
|
surface_snapshot: "time-sleep.surface.lower",
|
|
checked_snapshot: "time-sleep.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/owned-string-concat.slo",
|
|
surface_snapshot: "owned-string-concat.surface.lower",
|
|
checked_snapshot: "owned-string-concat.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "tests/standard-io-host-env.slo",
|
|
surface_snapshot: "standard-io-host-env.surface.lower",
|
|
checked_snapshot: "standard-io-host-env.checked.lower",
|
|
},
|
|
LoweringInspectorCase {
|
|
source: "examples/vec-i32.slo",
|
|
surface_snapshot: "vec-i32.surface.lower",
|
|
checked_snapshot: "vec-i32.checked.lower",
|
|
},
|
|
];
|
|
|
|
const GLAGOL_TEST_FIXTURES: &[&str] = &[
|
|
"array-direct-scalars-value-flow.slo",
|
|
"array-direct-scalars.slo",
|
|
"array-enum.slo",
|
|
"array-string-value-flow.slo",
|
|
"array-string.slo",
|
|
"array-struct-elements.slo",
|
|
"array-struct-fields.slo",
|
|
"array-value-flow.slo",
|
|
"array.slo",
|
|
"boolean-logic.slo",
|
|
"canonical.fmt",
|
|
"checked-i64-to-i32-conversion.slo",
|
|
"composite-locals.slo",
|
|
"composite-struct-fields.slo",
|
|
"comments.slo",
|
|
"enum-basic.slo",
|
|
"enum-payload-direct-scalars.slo",
|
|
"enum-payload-structs.slo",
|
|
"enum-payload-i32.slo",
|
|
"enum-struct-fields.slo",
|
|
"f64-to-i32-result.slo",
|
|
"f64-to-i64-result.slo",
|
|
"f64-to-string.slo",
|
|
"f64-numeric-primitive.slo",
|
|
"formatter-stability-v1.fmt",
|
|
"host-io.slo",
|
|
"host-io-result.slo",
|
|
"i64-numeric-primitive.slo",
|
|
"if.slo",
|
|
"integer-bitwise.slo",
|
|
"integer-remainder.slo",
|
|
"integer-to-string.slo",
|
|
"local-variables.slo",
|
|
"numeric-struct-fields.slo",
|
|
"numeric-widening-conversions.slo",
|
|
"option-result-flow.slo",
|
|
"option-result-match.slo",
|
|
"option-result-payload.slo",
|
|
"option-result.slo",
|
|
"owned-string-concat.slo",
|
|
"primitive-struct-fields.slo",
|
|
"print-bool.slo",
|
|
"random.slo",
|
|
"result-helpers.slo",
|
|
"standard-io-host-env.slo",
|
|
"standard-runtime.slo",
|
|
"stdin-result.slo",
|
|
"string-parse-i32-result.slo",
|
|
"string-parse-i64-result.slo",
|
|
"string-parse-u32-result.slo",
|
|
"string-parse-u64-result.slo",
|
|
"string-parse-f64-result.slo",
|
|
"string-parse-bool-result.slo",
|
|
"string-print.slo",
|
|
"string-value-flow.slo",
|
|
"struct-value-flow.slo",
|
|
"struct.slo",
|
|
"time-sleep.slo",
|
|
"top-level-test.fmt",
|
|
"top-level-test.slo",
|
|
"type-aliases.slo",
|
|
"u32-numeric-primitive.slo",
|
|
"u64-numeric-primitive.slo",
|
|
"unsafe.slo",
|
|
"unsigned-integer-to-string.slo",
|
|
"vec-i32.slo",
|
|
"while.slo",
|
|
];
|
|
|
|
const SLOVO_FORMATTER_FIXTURES: &[&str] = &[
|
|
"array-direct-scalars-value-flow.slo",
|
|
"array-direct-scalars.slo",
|
|
"array-enum.slo",
|
|
"array-string-value-flow.slo",
|
|
"array-string.slo",
|
|
"array-struct-elements.slo",
|
|
"array-struct-fields.slo",
|
|
"array-value-flow.slo",
|
|
"array.slo",
|
|
"boolean-logic.slo",
|
|
"canonical.slo",
|
|
"checked-i64-to-i32-conversion.slo",
|
|
"composite-locals.slo",
|
|
"composite-struct-fields.slo",
|
|
"comments.slo",
|
|
"enum-basic.slo",
|
|
"enum-payload-direct-scalars.slo",
|
|
"enum-payload-structs.slo",
|
|
"enum-payload-i32.slo",
|
|
"enum-struct-fields.slo",
|
|
"f64-to-i32-result.slo",
|
|
"f64-to-i64-result.slo",
|
|
"f64-to-string.slo",
|
|
"f64-numeric-primitive.slo",
|
|
"host-io.slo",
|
|
"host-io-result.slo",
|
|
"i64-numeric-primitive.slo",
|
|
"if.slo",
|
|
"integer-bitwise.slo",
|
|
"integer-remainder.slo",
|
|
"integer-to-string.slo",
|
|
"local-variables.slo",
|
|
"numeric-struct-fields.slo",
|
|
"numeric-widening-conversions.slo",
|
|
"option-result-flow.slo",
|
|
"option-result-match.slo",
|
|
"option-result-payload.slo",
|
|
"option-result.slo",
|
|
"owned-string-concat.slo",
|
|
"primitive-struct-fields.slo",
|
|
"print-bool.slo",
|
|
"random.slo",
|
|
"result-helpers.slo",
|
|
"standard-runtime.slo",
|
|
"std-source-layout-alpha.slo",
|
|
"stdin-result.slo",
|
|
"string-parse-i32-result.slo",
|
|
"string-parse-i64-result.slo",
|
|
"string-parse-u32-result.slo",
|
|
"string-parse-u64-result.slo",
|
|
"string-parse-f64-result.slo",
|
|
"string-parse-bool-result.slo",
|
|
"string-print.slo",
|
|
"string-value-flow.slo",
|
|
"struct-value-flow.slo",
|
|
"struct.slo",
|
|
"time-sleep.slo",
|
|
"top-level-test.slo",
|
|
"type-aliases.slo",
|
|
"u32-numeric-primitive.slo",
|
|
"u64-numeric-primitive.slo",
|
|
"unsafe.slo",
|
|
"unsigned-integer-to-string.slo",
|
|
"vec-bool.slo",
|
|
"vec-f64.slo",
|
|
"vec-i32.slo",
|
|
"vec-i64.slo",
|
|
"vec-string.slo",
|
|
"while.slo",
|
|
];
|
|
|
|
const SLOVO_V0_SUPPORTED_COMPATIBILITY_FIXTURES: &[&str] = &[
|
|
"add.slo",
|
|
"array.slo",
|
|
"if.slo",
|
|
"local-variables.slo",
|
|
"option-result.slo",
|
|
"struct.slo",
|
|
"top-level-test.slo",
|
|
"unsafe.slo",
|
|
"while.slo",
|
|
];
|
|
|
|
const SLOVO_V0_FORMATTER_COMPATIBILITY_FIXTURES: &[&str] = &[
|
|
"array.slo",
|
|
"canonical.slo",
|
|
"if.slo",
|
|
"local-variables.slo",
|
|
"option-result.slo",
|
|
"struct.slo",
|
|
"top-level-test.slo",
|
|
"unsafe.slo",
|
|
"while.slo",
|
|
];
|
|
|
|
const STANDARD_MATH_SOURCE_HELPERS_ALPHA: &[&str] = &[
|
|
"abs_i32",
|
|
"neg_i32",
|
|
"rem_i32",
|
|
"bit_and_i32",
|
|
"bit_or_i32",
|
|
"bit_xor_i32",
|
|
"is_even_i32",
|
|
"is_odd_i32",
|
|
"min_i32",
|
|
"max_i32",
|
|
"clamp_i32",
|
|
"square_i32",
|
|
"cube_i32",
|
|
"is_zero_i32",
|
|
"is_positive_i32",
|
|
"is_negative_i32",
|
|
"in_range_i32",
|
|
"abs_i64",
|
|
"neg_i64",
|
|
"rem_i64",
|
|
"bit_and_i64",
|
|
"bit_or_i64",
|
|
"bit_xor_i64",
|
|
"is_even_i64",
|
|
"is_odd_i64",
|
|
"min_i64",
|
|
"max_i64",
|
|
"clamp_i64",
|
|
"square_i64",
|
|
"cube_i64",
|
|
"is_zero_i64",
|
|
"is_positive_i64",
|
|
"is_negative_i64",
|
|
"in_range_i64",
|
|
"abs_f64",
|
|
"neg_f64",
|
|
"min_f64",
|
|
"max_f64",
|
|
"clamp_f64",
|
|
"square_f64",
|
|
"cube_f64",
|
|
"is_zero_f64",
|
|
"is_positive_f64",
|
|
"is_negative_f64",
|
|
"in_range_f64",
|
|
];
|
|
|
|
const STANDARD_OPTION_SOURCE_HELPERS_ALPHA: &[&str] = &[
|
|
"some_i32",
|
|
"none_i32",
|
|
"is_some_i32",
|
|
"is_none_i32",
|
|
"unwrap_some_i32",
|
|
"unwrap_or_i32",
|
|
"some_u32",
|
|
"none_u32",
|
|
"is_some_u32",
|
|
"is_none_u32",
|
|
"unwrap_some_u32",
|
|
"unwrap_or_u32",
|
|
"some_i64",
|
|
"none_i64",
|
|
"is_some_i64",
|
|
"is_none_i64",
|
|
"unwrap_some_i64",
|
|
"unwrap_or_i64",
|
|
"some_u64",
|
|
"none_u64",
|
|
"is_some_u64",
|
|
"is_none_u64",
|
|
"unwrap_some_u64",
|
|
"unwrap_or_u64",
|
|
"some_f64",
|
|
"none_f64",
|
|
"is_some_f64",
|
|
"is_none_f64",
|
|
"unwrap_some_f64",
|
|
"unwrap_or_f64",
|
|
"some_bool",
|
|
"none_bool",
|
|
"is_some_bool",
|
|
"is_none_bool",
|
|
"unwrap_some_bool",
|
|
"unwrap_or_bool",
|
|
"some_string",
|
|
"none_string",
|
|
"is_some_string",
|
|
"is_none_string",
|
|
"unwrap_some_string",
|
|
"unwrap_or_string",
|
|
];
|
|
|
|
const STANDARD_OPTION_RESULT_BRIDGE_HELPERS_ALPHA: &[&str] = &[
|
|
"some_or_err_i32",
|
|
"some_or_err_u32",
|
|
"some_or_err_i64",
|
|
"some_or_err_u64",
|
|
"some_or_err_f64",
|
|
"some_or_err_bool",
|
|
"some_or_err_string",
|
|
];
|
|
|
|
const STANDARD_TIME_SOURCE_FACADE_ALPHA: &[&str] = &["monotonic_ms", "sleep_ms_zero"];
|
|
|
|
const STANDARD_RANDOM_SOURCE_FACADE_ALPHA: &[&str] = &["random_i32", "random_i32_non_negative"];
|
|
|
|
const STANDARD_ENV_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"get",
|
|
"get_result",
|
|
"get_option",
|
|
"has",
|
|
"get_or",
|
|
"get_i32_result",
|
|
"get_i32_option",
|
|
"get_i32_or_zero",
|
|
"get_i32_or",
|
|
"get_u32_result",
|
|
"get_u32_option",
|
|
"get_u32_or_zero",
|
|
"get_u32_or",
|
|
"get_i64_result",
|
|
"get_i64_option",
|
|
"get_i64_or_zero",
|
|
"get_i64_or",
|
|
"get_u64_result",
|
|
"get_u64_option",
|
|
"get_u64_or_zero",
|
|
"get_u64_or",
|
|
"get_f64_result",
|
|
"get_f64_option",
|
|
"get_f64_or_zero",
|
|
"get_f64_or",
|
|
"get_bool_result",
|
|
"get_bool_option",
|
|
"get_bool_or_false",
|
|
"get_bool_or",
|
|
];
|
|
|
|
const STANDARD_FS_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"read_text",
|
|
"read_text_result",
|
|
"read_text_option",
|
|
"write_text_status",
|
|
"write_text_result",
|
|
"exists",
|
|
"is_file",
|
|
"is_dir",
|
|
"remove_file_result",
|
|
"create_dir_result",
|
|
"remove_file_ok",
|
|
"create_dir_ok",
|
|
"open_text_read_result",
|
|
"read_open_text_result",
|
|
"close_result",
|
|
"read_text_via_handle_result",
|
|
"close_ok",
|
|
"read_text_or",
|
|
"write_text_ok",
|
|
"read_i32_result",
|
|
"read_i32_option",
|
|
"read_i32_or_zero",
|
|
"read_i32_or",
|
|
"read_u32_result",
|
|
"read_u32_option",
|
|
"read_u32_or_zero",
|
|
"read_u32_or",
|
|
"read_i64_result",
|
|
"read_i64_option",
|
|
"read_i64_or_zero",
|
|
"read_i64_or",
|
|
"read_u64_result",
|
|
"read_u64_option",
|
|
"read_u64_or_zero",
|
|
"read_u64_or",
|
|
"read_f64_result",
|
|
"read_f64_option",
|
|
"read_f64_or_zero",
|
|
"read_f64_or",
|
|
"read_bool_result",
|
|
"read_bool_option",
|
|
"read_bool_or_false",
|
|
"read_bool_or",
|
|
];
|
|
|
|
const STANDARD_NET_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"tcp_connect_loopback_result",
|
|
"tcp_listen_loopback_result",
|
|
"tcp_bound_port_result",
|
|
"tcp_accept_result",
|
|
"tcp_read_all_result",
|
|
"tcp_write_text_result",
|
|
"tcp_close_result",
|
|
"tcp_write_text_ok",
|
|
"tcp_close_ok",
|
|
];
|
|
|
|
const STANDARD_NET_RUNTIME_NAMES: &[&str] = &[
|
|
"std.net.tcp_connect_loopback_result",
|
|
"std.net.tcp_listen_loopback_result",
|
|
"std.net.tcp_bound_port_result",
|
|
"std.net.tcp_accept_result",
|
|
"std.net.tcp_read_all_result",
|
|
"std.net.tcp_write_text_result",
|
|
"std.net.tcp_close_result",
|
|
];
|
|
|
|
const STANDARD_JSON_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"quote_string",
|
|
"null_value",
|
|
"bool_value",
|
|
"i32_value",
|
|
"u32_value",
|
|
"i64_value",
|
|
"u64_value",
|
|
"f64_value",
|
|
"parse_bool_value_result",
|
|
"parse_i32_value_result",
|
|
"parse_u32_value_result",
|
|
"parse_i64_value_result",
|
|
"parse_u64_value_result",
|
|
"parse_f64_value_result",
|
|
"parse_null_value_result",
|
|
"field_string",
|
|
"field_bool",
|
|
"field_i32",
|
|
"field_u32",
|
|
"field_i64",
|
|
"field_u64",
|
|
"field_f64",
|
|
"field_null",
|
|
"array0",
|
|
"array1",
|
|
"array2",
|
|
"array3",
|
|
"object0",
|
|
"object1",
|
|
"object2",
|
|
"object3",
|
|
];
|
|
|
|
const STANDARD_JSON_RUNTIME_NAMES: &[&str] = &[
|
|
"std.json.quote_string",
|
|
"std.string.concat",
|
|
"std.num.i32_to_string",
|
|
"std.num.u32_to_string",
|
|
"std.num.i64_to_string",
|
|
"std.num.u64_to_string",
|
|
"std.num.f64_to_string",
|
|
"std.json.parse_bool_value_result",
|
|
"std.json.parse_i32_value_result",
|
|
"std.json.parse_u32_value_result",
|
|
"std.json.parse_i64_value_result",
|
|
"std.json.parse_u64_value_result",
|
|
"std.json.parse_f64_value_result",
|
|
];
|
|
|
|
const STANDARD_PROCESS_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"argc",
|
|
"arg",
|
|
"arg_result",
|
|
"arg_option",
|
|
"has_arg",
|
|
"arg_or",
|
|
"arg_or_empty",
|
|
"arg_i32_result",
|
|
"arg_i32_option",
|
|
"arg_i32_or_zero",
|
|
"arg_i32_or",
|
|
"arg_u32_result",
|
|
"arg_u32_option",
|
|
"arg_u32_or_zero",
|
|
"arg_u32_or",
|
|
"arg_i64_result",
|
|
"arg_i64_option",
|
|
"arg_i64_or_zero",
|
|
"arg_i64_or",
|
|
"arg_u64_result",
|
|
"arg_u64_option",
|
|
"arg_u64_or_zero",
|
|
"arg_u64_or",
|
|
"arg_f64_result",
|
|
"arg_f64_option",
|
|
"arg_f64_or_zero",
|
|
"arg_f64_or",
|
|
"arg_bool_result",
|
|
"arg_bool_option",
|
|
"arg_bool_or_false",
|
|
"arg_bool_or",
|
|
];
|
|
|
|
const STANDARD_STRING_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"len",
|
|
"concat",
|
|
"byte_at_result",
|
|
"slice_result",
|
|
"starts_with",
|
|
"ends_with",
|
|
"parse_i32_result",
|
|
"parse_i32_option",
|
|
"parse_u32_result",
|
|
"parse_u32_option",
|
|
"parse_i64_result",
|
|
"parse_i64_option",
|
|
"parse_u64_result",
|
|
"parse_u64_option",
|
|
"parse_f64_result",
|
|
"parse_f64_option",
|
|
"parse_bool_result",
|
|
"parse_bool_option",
|
|
"parse_i32_or_zero",
|
|
"parse_u32_or_zero",
|
|
"parse_i64_or_zero",
|
|
"parse_u64_or_zero",
|
|
"parse_f64_or_zero",
|
|
"parse_bool_or_false",
|
|
"parse_i32_or",
|
|
"parse_u32_or",
|
|
"parse_i64_or",
|
|
"parse_u64_or",
|
|
"parse_f64_or",
|
|
"parse_bool_or",
|
|
];
|
|
|
|
const STANDARD_NUM_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"i32_to_i64",
|
|
"i32_to_f64",
|
|
"i64_to_f64",
|
|
"i64_to_i32_result",
|
|
"f64_to_i32_result",
|
|
"f64_to_i64_result",
|
|
"i32_to_string",
|
|
"u32_to_string",
|
|
"i64_to_string",
|
|
"u64_to_string",
|
|
"f64_to_string",
|
|
"i64_to_i32_or",
|
|
"f64_to_i32_or",
|
|
"f64_to_i64_or",
|
|
];
|
|
|
|
const STANDARD_IO_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"print_i32_zero",
|
|
"print_i64_zero",
|
|
"print_u32_zero",
|
|
"print_u64_zero",
|
|
"print_f64_zero",
|
|
"print_string_zero",
|
|
"print_bool_zero",
|
|
"print_i32_value",
|
|
"print_i64_value",
|
|
"print_u32_value",
|
|
"print_u64_value",
|
|
"print_f64_value",
|
|
"print_string_value",
|
|
"print_bool_value",
|
|
"read_stdin_result",
|
|
"read_stdin_option",
|
|
"read_stdin_or",
|
|
"read_stdin_i32_result",
|
|
"read_stdin_i32_option",
|
|
"read_stdin_i32_or_zero",
|
|
"read_stdin_i32_or",
|
|
"read_stdin_u32_result",
|
|
"read_stdin_u32_option",
|
|
"read_stdin_u32_or_zero",
|
|
"read_stdin_u32_or",
|
|
"read_stdin_i64_result",
|
|
"read_stdin_i64_option",
|
|
"read_stdin_i64_or_zero",
|
|
"read_stdin_i64_or",
|
|
"read_stdin_u64_result",
|
|
"read_stdin_u64_option",
|
|
"read_stdin_u64_or_zero",
|
|
"read_stdin_u64_or",
|
|
"read_stdin_f64_result",
|
|
"read_stdin_f64_option",
|
|
"read_stdin_f64_or_zero",
|
|
"read_stdin_f64_or",
|
|
"read_stdin_bool_result",
|
|
"read_stdin_bool_option",
|
|
"read_stdin_bool_or_false",
|
|
"read_stdin_bool_or",
|
|
];
|
|
|
|
const STANDARD_CLI_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"arg_text_result",
|
|
"arg_text_option",
|
|
"arg_i32_result",
|
|
"arg_i32_option",
|
|
"arg_i32_or_zero",
|
|
"arg_i32_or",
|
|
"arg_u32_result",
|
|
"arg_u32_option",
|
|
"arg_u32_or_zero",
|
|
"arg_u32_or",
|
|
"arg_i64_result",
|
|
"arg_i64_option",
|
|
"arg_i64_or_zero",
|
|
"arg_i64_or",
|
|
"arg_u64_result",
|
|
"arg_u64_option",
|
|
"arg_u64_or_zero",
|
|
"arg_u64_or",
|
|
"arg_f64_result",
|
|
"arg_f64_option",
|
|
"arg_f64_or_zero",
|
|
"arg_f64_or",
|
|
"arg_bool_result",
|
|
"arg_bool_option",
|
|
"arg_bool_or_false",
|
|
"arg_bool_or",
|
|
];
|
|
|
|
const STANDARD_STRING_PARSE_RESULT_HELPERS_ALPHA: &[&str] = &[
|
|
"parse_i32_result",
|
|
"parse_u32_result",
|
|
"parse_i64_result",
|
|
"parse_u64_result",
|
|
"parse_f64_result",
|
|
"parse_bool_result",
|
|
];
|
|
|
|
const STANDARD_CLI_LOCAL_SOURCE_FALLBACK_EXPECTED_OUTPUT: &str = concat!(
|
|
"test \"explicit local cli arg text missing\" ... ok\n",
|
|
"test \"explicit local cli arg text option\" ... ok\n",
|
|
"test \"explicit local cli arg i32 missing\" ... ok\n",
|
|
"test \"explicit local cli arg i32 fallback missing\" ... ok\n",
|
|
"test \"explicit local cli arg u32 missing\" ... ok\n",
|
|
"test \"explicit local cli arg u32 fallback missing\" ... ok\n",
|
|
"test \"explicit local cli arg i64 missing\" ... ok\n",
|
|
"test \"explicit local cli arg i64 fallback missing\" ... ok\n",
|
|
"test \"explicit local cli arg u64 missing\" ... ok\n",
|
|
"test \"explicit local cli arg u64 fallback missing\" ... ok\n",
|
|
"test \"explicit local cli arg f64 missing\" ... ok\n",
|
|
"test \"explicit local cli arg f64 fallback missing\" ... ok\n",
|
|
"test \"explicit local cli arg bool missing\" ... ok\n",
|
|
"test \"explicit local cli arg bool fallback missing\" ... ok\n",
|
|
"test \"explicit local cli typed option\" ... ok\n",
|
|
"test \"explicit local cli typed custom fallback\" ... ok\n",
|
|
"test \"explicit local cli facade all\" ... ok\n",
|
|
"17 test(s) passed\n",
|
|
);
|
|
|
|
const STANDARD_VEC_I32_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"empty",
|
|
"append",
|
|
"len",
|
|
"at",
|
|
"singleton",
|
|
"append2",
|
|
"append3",
|
|
"pair",
|
|
"triple",
|
|
"repeat",
|
|
"range",
|
|
"range_from_zero",
|
|
"is_empty",
|
|
"index_or",
|
|
"first_or",
|
|
"last_or",
|
|
"index_option",
|
|
"first_option",
|
|
"last_option",
|
|
"index_of_option",
|
|
"last_index_of_option",
|
|
"count_of",
|
|
"contains",
|
|
"sum",
|
|
"concat",
|
|
"take",
|
|
"starts_with",
|
|
"without_prefix",
|
|
"ends_with",
|
|
"without_suffix",
|
|
"drop",
|
|
"reverse",
|
|
"subvec",
|
|
"insert_at",
|
|
"insert_range",
|
|
"replace_at",
|
|
"replace_range",
|
|
"remove_at",
|
|
"remove_range",
|
|
];
|
|
|
|
const STANDARD_VEC_I64_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"empty",
|
|
"append",
|
|
"len",
|
|
"at",
|
|
"singleton",
|
|
"append2",
|
|
"append3",
|
|
"pair",
|
|
"triple",
|
|
"is_empty",
|
|
"index_or",
|
|
"first_or",
|
|
"last_or",
|
|
"index_option",
|
|
"first_option",
|
|
"last_option",
|
|
"index_of_option",
|
|
"last_index_of_option",
|
|
"contains",
|
|
"count_of",
|
|
"sum",
|
|
"concat",
|
|
"take",
|
|
"starts_with",
|
|
"without_prefix",
|
|
"ends_with",
|
|
"without_suffix",
|
|
"drop",
|
|
"reverse",
|
|
"subvec",
|
|
"insert_at",
|
|
"insert_range",
|
|
"replace_at",
|
|
"replace_range",
|
|
"remove_at",
|
|
"remove_range",
|
|
];
|
|
|
|
const STANDARD_VEC_F64_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"empty",
|
|
"append",
|
|
"len",
|
|
"at",
|
|
"singleton",
|
|
"append2",
|
|
"append3",
|
|
"pair",
|
|
"triple",
|
|
"is_empty",
|
|
"index_or",
|
|
"first_or",
|
|
"last_or",
|
|
"index_option",
|
|
"first_option",
|
|
"last_option",
|
|
"index_of_option",
|
|
"last_index_of_option",
|
|
"contains",
|
|
"count_of",
|
|
"sum",
|
|
"concat",
|
|
"take",
|
|
"starts_with",
|
|
"without_prefix",
|
|
"ends_with",
|
|
"without_suffix",
|
|
"drop",
|
|
"reverse",
|
|
"subvec",
|
|
"insert_at",
|
|
"insert_range",
|
|
"replace_at",
|
|
"replace_range",
|
|
"remove_at",
|
|
"remove_range",
|
|
];
|
|
|
|
const STANDARD_VEC_BOOL_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"empty",
|
|
"append",
|
|
"len",
|
|
"at",
|
|
"singleton",
|
|
"append2",
|
|
"append3",
|
|
"pair",
|
|
"triple",
|
|
"is_empty",
|
|
"index_or",
|
|
"first_or",
|
|
"last_or",
|
|
"index_option",
|
|
"first_option",
|
|
"last_option",
|
|
"index_of_option",
|
|
"last_index_of_option",
|
|
"contains",
|
|
"count_of",
|
|
"concat",
|
|
"take",
|
|
"drop",
|
|
"reverse",
|
|
"subvec",
|
|
"insert_at",
|
|
"insert_range",
|
|
"replace_at",
|
|
"replace_range",
|
|
"remove_at",
|
|
"remove_range",
|
|
];
|
|
|
|
const STANDARD_VEC_STRING_SOURCE_FACADE_ALPHA: &[&str] = &[
|
|
"empty",
|
|
"append",
|
|
"len",
|
|
"at",
|
|
"singleton",
|
|
"append2",
|
|
"append3",
|
|
"pair",
|
|
"triple",
|
|
"is_empty",
|
|
"index_or",
|
|
"first_or",
|
|
"last_or",
|
|
"index_option",
|
|
"first_option",
|
|
"last_option",
|
|
"index_of_option",
|
|
"last_index_of_option",
|
|
"contains",
|
|
"count_of",
|
|
"concat",
|
|
"take",
|
|
"drop",
|
|
"reverse",
|
|
"subvec",
|
|
"insert_at",
|
|
"insert_range",
|
|
"replace_at",
|
|
"replace_range",
|
|
"remove_at",
|
|
"remove_range",
|
|
];
|
|
|
|
const STANDARD_ENV_MISSING_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_UNLIKELY_MISSING";
|
|
const STANDARD_ENV_PRESENT_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_PRESENT";
|
|
const STANDARD_ENV_PRESENT_VALUE: &str = "glagol-std-layout-local-env-alpha-value";
|
|
const STANDARD_ENV_PRESENT_I32_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_PRESENT_I32";
|
|
const STANDARD_ENV_PRESENT_I32_VALUE: &str = "42";
|
|
const STANDARD_ENV_PRESENT_U32_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_PRESENT_U32";
|
|
const STANDARD_ENV_PRESENT_U32_VALUE: &str = "42";
|
|
const STANDARD_ENV_PRESENT_I64_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_PRESENT_I64";
|
|
const STANDARD_ENV_PRESENT_I64_VALUE: &str = "42000000000";
|
|
const STANDARD_ENV_PRESENT_U64_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_PRESENT_U64";
|
|
const STANDARD_ENV_PRESENT_U64_VALUE: &str = "4294967296";
|
|
const STANDARD_ENV_PRESENT_F64_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_PRESENT_F64";
|
|
const STANDARD_ENV_PRESENT_F64_VALUE: &str = "42.5";
|
|
const STANDARD_ENV_PRESENT_BOOL_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_PRESENT_BOOL";
|
|
const STANDARD_ENV_PRESENT_BOOL_VALUE: &str = "true";
|
|
const STANDARD_ENV_INVALID_NAME: &str = "GLAGOL_STD_LAYOUT_LOCAL_ENV_ALPHA_INVALID";
|
|
const STANDARD_ENV_INVALID_VALUE: &str = "bad";
|
|
const STANDARD_IMPORT_ENV_MISSING_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_UNLIKELY_MISSING";
|
|
const STANDARD_IMPORT_ENV_PRESENT_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_PRESENT";
|
|
const STANDARD_IMPORT_ENV_PRESENT_VALUE: &str = "glagol-std-import-env-alpha-value";
|
|
const STANDARD_IMPORT_ENV_PRESENT_I32_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_PRESENT_I32";
|
|
const STANDARD_IMPORT_ENV_PRESENT_I32_VALUE: &str = "42";
|
|
const STANDARD_IMPORT_ENV_PRESENT_U32_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_PRESENT_U32";
|
|
const STANDARD_IMPORT_ENV_PRESENT_U32_VALUE: &str = "42";
|
|
const STANDARD_IMPORT_ENV_PRESENT_I64_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_PRESENT_I64";
|
|
const STANDARD_IMPORT_ENV_PRESENT_I64_VALUE: &str = "42000000000";
|
|
const STANDARD_IMPORT_ENV_PRESENT_U64_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_PRESENT_U64";
|
|
const STANDARD_IMPORT_ENV_PRESENT_U64_VALUE: &str = "4294967296";
|
|
const STANDARD_IMPORT_ENV_PRESENT_F64_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_PRESENT_F64";
|
|
const STANDARD_IMPORT_ENV_PRESENT_F64_VALUE: &str = "42.5";
|
|
const STANDARD_IMPORT_ENV_PRESENT_BOOL_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_PRESENT_BOOL";
|
|
const STANDARD_IMPORT_ENV_PRESENT_BOOL_VALUE: &str = "true";
|
|
const STANDARD_IMPORT_ENV_INVALID_NAME: &str = "GLAGOL_STD_IMPORT_ENV_ALPHA_INVALID";
|
|
const STANDARD_IMPORT_ENV_INVALID_VALUE: &str = "bad";
|
|
|
|
const STANDARD_RESULT_SOURCE_HELPERS_ALPHA: &[&str] = &[
|
|
"ok_i32",
|
|
"err_i32",
|
|
"is_ok_i32",
|
|
"is_err_i32",
|
|
"unwrap_ok_i32",
|
|
"unwrap_err_i32",
|
|
"unwrap_or_i32",
|
|
"ok_u32",
|
|
"err_u32",
|
|
"is_ok_u32",
|
|
"is_err_u32",
|
|
"unwrap_ok_u32",
|
|
"unwrap_err_u32",
|
|
"unwrap_or_u32",
|
|
"ok_i64",
|
|
"err_i64",
|
|
"is_err_i64",
|
|
"unwrap_err_i64",
|
|
"unwrap_or_i64",
|
|
"ok_u64",
|
|
"err_u64",
|
|
"is_ok_u64",
|
|
"is_err_u64",
|
|
"unwrap_ok_u64",
|
|
"unwrap_err_u64",
|
|
"unwrap_or_u64",
|
|
"ok_string",
|
|
"err_string",
|
|
"is_err_string",
|
|
"unwrap_err_string",
|
|
"unwrap_or_string",
|
|
"ok_f64",
|
|
"err_f64",
|
|
"is_err_f64",
|
|
"unwrap_err_f64",
|
|
"unwrap_or_f64",
|
|
"ok_bool",
|
|
"err_bool",
|
|
"is_ok_bool",
|
|
"is_err_bool",
|
|
"unwrap_ok_bool",
|
|
"unwrap_err_bool",
|
|
"unwrap_or_bool",
|
|
];
|
|
|
|
const STANDARD_RESULT_OPTION_BRIDGE_HELPERS_ALPHA: &[&str] = &[
|
|
"ok_or_none_i32",
|
|
"ok_or_none_u32",
|
|
"ok_or_none_i64",
|
|
"ok_or_none_u64",
|
|
"ok_or_none_string",
|
|
"ok_or_none_f64",
|
|
"ok_or_none_bool",
|
|
];
|
|
|
|
const STANDARD_RESULT_SOURCE_SEARCH_ALPHA: &[&str] = &[
|
|
"is_ok_i32",
|
|
"is_err_i32",
|
|
"unwrap_ok_i32",
|
|
"unwrap_err_i32",
|
|
"unwrap_or_i32",
|
|
"is_ok_u32",
|
|
"is_err_u32",
|
|
"unwrap_ok_u32",
|
|
"unwrap_err_u32",
|
|
"unwrap_or_u32",
|
|
"is_ok_i64",
|
|
"is_err_i64",
|
|
"unwrap_ok_i64",
|
|
"unwrap_err_i64",
|
|
"unwrap_or_i64",
|
|
"is_ok_u64",
|
|
"is_err_u64",
|
|
"unwrap_ok_u64",
|
|
"unwrap_err_u64",
|
|
"unwrap_or_u64",
|
|
"is_ok_string",
|
|
"is_err_string",
|
|
"unwrap_ok_string",
|
|
"unwrap_err_string",
|
|
"unwrap_or_string",
|
|
"is_ok_f64",
|
|
"is_err_f64",
|
|
"unwrap_ok_f64",
|
|
"unwrap_err_f64",
|
|
"unwrap_or_f64",
|
|
"is_ok_bool",
|
|
"is_err_bool",
|
|
"unwrap_ok_bool",
|
|
"unwrap_err_bool",
|
|
"unwrap_or_bool",
|
|
];
|
|
|
|
struct LoweringInspectorCase {
|
|
source: &'static str,
|
|
surface_snapshot: &'static str,
|
|
checked_snapshot: &'static str,
|
|
}
|
|
|
|
#[test]
|
|
fn promotion_gate_artifacts_are_aligned() {
|
|
let repo = repo_root();
|
|
let glagol_add = repo.join("examples/add.slo");
|
|
let glagol_array_direct_scalars = repo.join("examples/array-direct-scalars.slo");
|
|
let glagol_array_direct_scalars_value_flow =
|
|
repo.join("examples/array-direct-scalars-value-flow.slo");
|
|
let glagol_array_enum = repo.join("examples/array-enum.slo");
|
|
let glagol_array_struct_elements = repo.join("examples/array-struct-elements.slo");
|
|
let glagol_array_struct_fields = repo.join("examples/array-struct-fields.slo");
|
|
let glagol_array_string = repo.join("examples/array-string.slo");
|
|
let glagol_array_string_value_flow = repo.join("examples/array-string-value-flow.slo");
|
|
let glagol_array = repo.join("examples/array.slo");
|
|
let glagol_array_value_flow = repo.join("examples/array-value-flow.slo");
|
|
let glagol_boolean_logic = repo.join("examples/boolean-logic.slo");
|
|
let glagol_checked_i64_to_i32 = repo.join("examples/checked-i64-to-i32-conversion.slo");
|
|
let glagol_enum_basic = repo.join("examples/enum-basic.slo");
|
|
let glagol_enum_payload_direct_scalars = repo.join("examples/enum-payload-direct-scalars.slo");
|
|
let glagol_enum_payload_structs = repo.join("examples/enum-payload-structs.slo");
|
|
let glagol_enum_payload_i32 = repo.join("examples/enum-payload-i32.slo");
|
|
let glagol_enum_struct_field = repo.join("examples/enum-struct-fields.slo");
|
|
let glagol_host_io = repo.join("examples/host-io.slo");
|
|
let glagol_host_io_result = repo.join("examples/host-io-result.slo");
|
|
let glagol_if = repo.join("examples/if.slo");
|
|
let glagol_integer_bitwise = repo.join("examples/integer-bitwise.slo");
|
|
let glagol_integer_remainder = repo.join("examples/integer-remainder.slo");
|
|
let glagol_integer_to_string = repo.join("examples/integer-to-string.slo");
|
|
let glagol_f64_to_string = repo.join("examples/f64-to-string.slo");
|
|
let glagol_f64_to_i32_result = repo.join("examples/f64-to-i32-result.slo");
|
|
let glagol_f64_to_i64_result = repo.join("examples/f64-to-i64-result.slo");
|
|
let glagol_composite = repo.join("examples/composite-locals.slo");
|
|
let glagol_composite_struct_fields = repo.join("examples/composite-struct-fields.slo");
|
|
let glagol_local = repo.join("examples/local-variables.slo");
|
|
let glagol_numeric_struct_fields = repo.join("examples/numeric-struct-fields.slo");
|
|
let glagol_numeric_widening = repo.join("examples/numeric-widening-conversions.slo");
|
|
let glagol_option_result = repo.join("examples/option-result.slo");
|
|
let glagol_option_result_flow = repo.join("examples/option-result-flow.slo");
|
|
let glagol_option_result_match = repo.join("examples/option-result-match.slo");
|
|
let glagol_option_result_payload = repo.join("examples/option-result-payload.slo");
|
|
let glagol_owned_string_concat = repo.join("examples/owned-string-concat.slo");
|
|
let glagol_print_bool = repo.join("examples/print-bool.slo");
|
|
let glagol_primitive_struct_fields = repo.join("examples/primitive-struct-fields.slo");
|
|
let glagol_random = repo.join("examples/random.slo");
|
|
let glagol_stdin_result = repo.join("examples/stdin-result.slo");
|
|
let glagol_string_parse_i32_result = repo.join("examples/string-parse-i32-result.slo");
|
|
let glagol_string_parse_i64_result = repo.join("examples/string-parse-i64-result.slo");
|
|
let glagol_string_parse_f64_result = repo.join("examples/string-parse-f64-result.slo");
|
|
let glagol_string_parse_bool_result = repo.join("examples/string-parse-bool-result.slo");
|
|
let glagol_result_helpers = repo.join("examples/result-helpers.slo");
|
|
let glagol_result_f64_bool_match = repo.join("examples/result-f64-bool-match.slo");
|
|
let glagol_standard_runtime = repo.join("examples/standard-runtime.slo");
|
|
let glagol_time_sleep = repo.join("examples/time-sleep.slo");
|
|
let glagol_string_print = repo.join("examples/string-print.slo");
|
|
let glagol_string_value_flow = repo.join("examples/string-value-flow.slo");
|
|
let glagol_struct = repo.join("examples/struct.slo");
|
|
let glagol_struct_value_flow = repo.join("examples/struct-value-flow.slo");
|
|
let glagol_unsafe = repo.join("examples/unsafe.slo");
|
|
let glagol_vec_i32 = repo.join("examples/vec-i32.slo");
|
|
let _glagol_vec_f64 = repo.join("examples/vec-f64.slo");
|
|
let _glagol_vec_bool = repo.join("examples/vec-bool.slo");
|
|
let _glagol_vec_string = repo.join("examples/vec-string.slo");
|
|
let glagol_while = repo.join("examples/while.slo");
|
|
let glagol_project_enum_imports = repo.join("examples/projects/enum-imports");
|
|
let glagol_project_std_layout_local_math = repo.join("examples/projects/std-layout-local-math");
|
|
let glagol_project_std_layout_local_num = repo.join("examples/projects/std-layout-local-num");
|
|
let glagol_project_std_layout_local_option =
|
|
repo.join("examples/projects/std-layout-local-option");
|
|
let glagol_project_std_layout_local_process =
|
|
repo.join("examples/projects/std-layout-local-process");
|
|
let glagol_project_std_layout_local_result =
|
|
repo.join("examples/projects/std-layout-local-result");
|
|
let glagol_project_std_layout_local_string =
|
|
repo.join("examples/projects/std-layout-local-string");
|
|
let glagol_project_std_layout_local_time = repo.join("examples/projects/std-layout-local-time");
|
|
let glagol_project_std_layout_local_random =
|
|
repo.join("examples/projects/std-layout-local-random");
|
|
let glagol_project_std_layout_local_env = repo.join("examples/projects/std-layout-local-env");
|
|
let glagol_project_std_layout_local_fs = repo.join("examples/projects/std-layout-local-fs");
|
|
let glagol_project_std_layout_local_net = repo.join("examples/projects/std-layout-local-net");
|
|
let glagol_project_std_layout_local_json = repo.join("examples/projects/std-layout-local-json");
|
|
let glagol_project_std_layout_local_io = repo.join("examples/projects/std-layout-local-io");
|
|
let glagol_project_std_layout_local_cli = repo.join("examples/projects/std-layout-local-cli");
|
|
let glagol_project_std_layout_local_vec_i32 =
|
|
repo.join("examples/projects/std-layout-local-vec_i32");
|
|
let glagol_project_std_layout_local_vec_i64 =
|
|
repo.join("examples/projects/std-layout-local-vec_i64");
|
|
let glagol_project_std_layout_local_vec_f64 =
|
|
repo.join("examples/projects/std-layout-local-vec_f64");
|
|
let glagol_project_std_layout_local_vec_bool =
|
|
repo.join("examples/projects/std-layout-local-vec_bool");
|
|
let glagol_project_std_layout_local_vec_string =
|
|
repo.join("examples/projects/std-layout-local-vec_string");
|
|
let glagol_project_std_import_math = repo.join("examples/projects/std-import-math");
|
|
let glagol_project_std_import_result = repo.join("examples/projects/std-import-result");
|
|
let glagol_project_std_import_option = repo.join("examples/projects/std-import-option");
|
|
let glagol_project_std_import_time = repo.join("examples/projects/std-import-time");
|
|
let glagol_project_std_import_random = repo.join("examples/projects/std-import-random");
|
|
let glagol_project_std_import_env = repo.join("examples/projects/std-import-env");
|
|
let glagol_project_std_import_fs = repo.join("examples/projects/std-import-fs");
|
|
let glagol_project_std_import_net = repo.join("examples/projects/std-import-net");
|
|
let glagol_project_std_import_json = repo.join("examples/projects/std-import-json");
|
|
let glagol_project_std_import_process = repo.join("examples/projects/std-import-process");
|
|
let glagol_project_std_import_string = repo.join("examples/projects/std-import-string");
|
|
let glagol_project_std_import_num = repo.join("examples/projects/std-import-num");
|
|
let glagol_project_std_import_io = repo.join("examples/projects/std-import-io");
|
|
let glagol_project_std_import_cli = repo.join("examples/projects/std-import-cli");
|
|
let glagol_project_std_import_vec_i32 = repo.join("examples/projects/std-import-vec_i32");
|
|
let glagol_project_std_import_vec_i64 = repo.join("examples/projects/std-import-vec_i64");
|
|
let glagol_project_std_import_vec_f64 = repo.join("examples/projects/std-import-vec_f64");
|
|
let glagol_project_std_import_vec_bool = repo.join("examples/projects/std-import-vec_bool");
|
|
let glagol_project_std_import_vec_string = repo.join("examples/projects/std-import-vec_string");
|
|
let glagol_workspace_std_import_option = repo.join("examples/workspaces/std-import-option");
|
|
let glagol_benchmark_math_loop = repo.join("benchmarks/math-loop");
|
|
let glagol_benchmark_branch_loop = repo.join("benchmarks/branch-loop");
|
|
let glagol_benchmark_parse_loop = repo.join("benchmarks/parse-loop");
|
|
let glagol_benchmark_json_quote_loop = repo.join("benchmarks/json-quote-loop");
|
|
let glagol_benchmark_array_index_loop = repo.join("benchmarks/array-index-loop");
|
|
let glagol_benchmark_string_eq_loop = repo.join("benchmarks/string-eq-loop");
|
|
let glagol_benchmark_array_struct_field_loop = repo.join("benchmarks/array-struct-field-loop");
|
|
let glagol_benchmark_enum_struct_payload_loop =
|
|
repo.join("benchmarks/enum-struct-payload-loop");
|
|
let glagol_benchmark_vec_i32_index_loop = repo.join("benchmarks/vec-i32-index-loop");
|
|
let glagol_benchmark_vec_string_eq_loop = repo.join("benchmarks/vec-string-eq-loop");
|
|
let formatter_canonical = repo.join("tests/canonical.fmt");
|
|
let array_direct_scalars_formatter = repo.join("tests/array-direct-scalars.slo");
|
|
let array_direct_scalars_value_flow_formatter =
|
|
repo.join("tests/array-direct-scalars-value-flow.slo");
|
|
let array_enum_formatter = repo.join("tests/array-enum.slo");
|
|
let array_struct_elements_formatter = repo.join("tests/array-struct-elements.slo");
|
|
let array_struct_fields_formatter = repo.join("tests/array-struct-fields.slo");
|
|
let array_string_formatter = repo.join("tests/array-string.slo");
|
|
let array_string_value_flow_formatter = repo.join("tests/array-string-value-flow.slo");
|
|
let array_formatter = repo.join("tests/array.slo");
|
|
let array_value_flow_formatter = repo.join("tests/array-value-flow.slo");
|
|
let boolean_logic_formatter = repo.join("tests/boolean-logic.slo");
|
|
let checked_i64_to_i32_formatter = repo.join("tests/checked-i64-to-i32-conversion.slo");
|
|
let host_io_formatter = repo.join("tests/host-io.slo");
|
|
let host_io_result_formatter = repo.join("tests/host-io-result.slo");
|
|
let if_formatter = repo.join("tests/if.slo");
|
|
let integer_bitwise_formatter = repo.join("tests/integer-bitwise.slo");
|
|
let integer_remainder_formatter = repo.join("tests/integer-remainder.slo");
|
|
let integer_to_string_formatter = repo.join("tests/integer-to-string.slo");
|
|
let f64_to_string_formatter = repo.join("tests/f64-to-string.slo");
|
|
let f64_to_i32_result_formatter = repo.join("tests/f64-to-i32-result.slo");
|
|
let f64_to_i64_result_formatter = repo.join("tests/f64-to-i64-result.slo");
|
|
let composite_formatter = repo.join("tests/composite-locals.slo");
|
|
let composite_struct_fields_formatter = repo.join("tests/composite-struct-fields.slo");
|
|
let local_formatter = repo.join("tests/local-variables.slo");
|
|
let numeric_struct_fields_formatter = repo.join("tests/numeric-struct-fields.slo");
|
|
let numeric_widening_formatter = repo.join("tests/numeric-widening-conversions.slo");
|
|
let option_result_formatter = repo.join("tests/option-result.slo");
|
|
let option_result_flow_formatter = repo.join("tests/option-result-flow.slo");
|
|
let option_result_match_formatter = repo.join("tests/option-result-match.slo");
|
|
let option_result_payload_formatter = repo.join("tests/option-result-payload.slo");
|
|
let owned_string_concat_formatter = repo.join("tests/owned-string-concat.slo");
|
|
let print_bool_formatter = repo.join("tests/print-bool.slo");
|
|
let primitive_struct_fields_formatter = repo.join("tests/primitive-struct-fields.slo");
|
|
let random_formatter = repo.join("tests/random.slo");
|
|
let stdin_result_formatter = repo.join("tests/stdin-result.slo");
|
|
let string_parse_i32_result_formatter = repo.join("tests/string-parse-i32-result.slo");
|
|
let string_parse_i64_result_formatter = repo.join("tests/string-parse-i64-result.slo");
|
|
let string_parse_f64_result_formatter = repo.join("tests/string-parse-f64-result.slo");
|
|
let string_parse_bool_result_formatter = repo.join("tests/string-parse-bool-result.slo");
|
|
let result_helpers_formatter = repo.join("tests/result-helpers.slo");
|
|
let standard_runtime_formatter = repo.join("tests/standard-runtime.slo");
|
|
let time_sleep_formatter = repo.join("tests/time-sleep.slo");
|
|
let string_print_formatter = repo.join("tests/string-print.slo");
|
|
let string_value_flow_formatter = repo.join("tests/string-value-flow.slo");
|
|
let struct_formatter = repo.join("tests/struct.slo");
|
|
let struct_value_flow_formatter = repo.join("tests/struct-value-flow.slo");
|
|
let unsafe_formatter = repo.join("tests/unsafe.slo");
|
|
let vec_i32_formatter = repo.join("tests/vec-i32.slo");
|
|
let while_formatter = repo.join("tests/while.slo");
|
|
let comments_formatter = repo.join("tests/comments.slo");
|
|
let enum_basic_formatter = repo.join("tests/enum-basic.slo");
|
|
let enum_payload_direct_scalars_formatter = repo.join("tests/enum-payload-direct-scalars.slo");
|
|
let enum_payload_structs_formatter = repo.join("tests/enum-payload-structs.slo");
|
|
let enum_payload_i32_formatter = repo.join("tests/enum-payload-i32.slo");
|
|
let enum_struct_field_formatter = repo.join("tests/enum-struct-fields.slo");
|
|
let formatter_stability_v1 = repo.join("tests/formatter-stability-v1.fmt");
|
|
|
|
assert_supported_fixtures(&repo);
|
|
assert_glagol_test_fixtures(&repo);
|
|
assert_lowering_inspector_fixture_inventory(&repo);
|
|
assert_same_supported_body(&glagol_add, &formatter_canonical);
|
|
assert_same_supported_body(
|
|
&glagol_array_direct_scalars,
|
|
&array_direct_scalars_formatter,
|
|
);
|
|
assert_same_supported_body(
|
|
&glagol_array_direct_scalars_value_flow,
|
|
&array_direct_scalars_value_flow_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_array_enum, &array_enum_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_array_struct_elements,
|
|
&array_struct_elements_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_array_struct_fields, &array_struct_fields_formatter);
|
|
assert_same_supported_body(&glagol_array_string, &array_string_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_array_string_value_flow,
|
|
&array_string_value_flow_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_array, &array_formatter);
|
|
assert_same_supported_body(&glagol_array_value_flow, &array_value_flow_formatter);
|
|
assert_same_supported_body(&glagol_boolean_logic, &boolean_logic_formatter);
|
|
assert_boolean_logic_tooling_matches_fixture(&glagol_boolean_logic);
|
|
assert_same_supported_body(&glagol_checked_i64_to_i32, &checked_i64_to_i32_formatter);
|
|
assert_same_supported_body(&glagol_enum_basic, &enum_basic_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_enum_payload_direct_scalars,
|
|
&enum_payload_direct_scalars_formatter,
|
|
);
|
|
assert_same_supported_body(
|
|
&glagol_enum_payload_structs,
|
|
&enum_payload_structs_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_enum_payload_i32, &enum_payload_i32_formatter);
|
|
assert_same_supported_body(&glagol_enum_struct_field, &enum_struct_field_formatter);
|
|
assert_same_supported_body(&glagol_host_io, &host_io_formatter);
|
|
assert_same_supported_body(&glagol_host_io_result, &host_io_result_formatter);
|
|
assert_same_supported_body(&glagol_if, &if_formatter);
|
|
assert_same_supported_body(&glagol_integer_bitwise, &integer_bitwise_formatter);
|
|
assert_integer_bitwise_tooling_matches_fixture(&glagol_integer_bitwise);
|
|
assert_same_supported_body(&glagol_integer_remainder, &integer_remainder_formatter);
|
|
assert_integer_remainder_tooling_matches_fixture(&glagol_integer_remainder);
|
|
assert_same_supported_body(&glagol_integer_to_string, &integer_to_string_formatter);
|
|
assert_same_supported_body(&glagol_f64_to_string, &f64_to_string_formatter);
|
|
assert_same_supported_body(&glagol_f64_to_i32_result, &f64_to_i32_result_formatter);
|
|
assert_same_supported_body(&glagol_f64_to_i64_result, &f64_to_i64_result_formatter);
|
|
assert_same_supported_body(&glagol_composite, &composite_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_composite_struct_fields,
|
|
&composite_struct_fields_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_local, &local_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_numeric_struct_fields,
|
|
&numeric_struct_fields_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_numeric_widening, &numeric_widening_formatter);
|
|
assert_same_supported_body(&glagol_option_result, &option_result_formatter);
|
|
assert_same_supported_body(&glagol_option_result_flow, &option_result_flow_formatter);
|
|
assert_same_supported_body(&glagol_option_result_match, &option_result_match_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_option_result_payload,
|
|
&option_result_payload_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_owned_string_concat, &owned_string_concat_formatter);
|
|
assert_same_supported_body(&glagol_print_bool, &print_bool_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_primitive_struct_fields,
|
|
&primitive_struct_fields_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_random, &random_formatter);
|
|
assert_same_supported_body(&glagol_stdin_result, &stdin_result_formatter);
|
|
assert_same_supported_body(
|
|
&glagol_string_parse_i32_result,
|
|
&string_parse_i32_result_formatter,
|
|
);
|
|
assert_same_supported_body(
|
|
&glagol_string_parse_i64_result,
|
|
&string_parse_i64_result_formatter,
|
|
);
|
|
assert_same_supported_body(
|
|
&glagol_string_parse_f64_result,
|
|
&string_parse_f64_result_formatter,
|
|
);
|
|
assert_same_supported_body(
|
|
&glagol_string_parse_bool_result,
|
|
&string_parse_bool_result_formatter,
|
|
);
|
|
assert_same_supported_body(&glagol_result_helpers, &result_helpers_formatter);
|
|
assert_same_supported_body(&glagol_standard_runtime, &standard_runtime_formatter);
|
|
assert_same_supported_body(&glagol_time_sleep, &time_sleep_formatter);
|
|
assert_same_supported_body(&glagol_string_print, &string_print_formatter);
|
|
assert_same_supported_body(&glagol_string_value_flow, &string_value_flow_formatter);
|
|
assert_same_supported_body(&glagol_struct, &struct_formatter);
|
|
assert_same_supported_body(&glagol_struct_value_flow, &struct_value_flow_formatter);
|
|
assert_same_supported_body(&glagol_unsafe, &unsafe_formatter);
|
|
assert_same_supported_body(&glagol_vec_i32, &vec_i32_formatter);
|
|
assert_same_supported_body(&glagol_while, &while_formatter);
|
|
assert_formatter_fixture_contract(&formatter_canonical);
|
|
|
|
assert_compiler_output_matches_supported_add_shape(&repo, &glagol_add);
|
|
assert_tree_printer_matches_fixture(&repo, &glagol_add);
|
|
assert_formatter_matches_fixture(&array_direct_scalars_formatter);
|
|
assert_formatter_matches_fixture(&array_direct_scalars_value_flow_formatter);
|
|
assert_formatter_matches_fixture(&array_enum_formatter);
|
|
assert_formatter_matches_fixture(&array_struct_elements_formatter);
|
|
assert_formatter_matches_fixture(&array_struct_fields_formatter);
|
|
assert_formatter_matches_fixture(&array_string_formatter);
|
|
assert_formatter_matches_fixture(&array_string_value_flow_formatter);
|
|
assert_formatter_matches_fixture(&formatter_canonical);
|
|
assert_formatter_matches_fixture(&boolean_logic_formatter);
|
|
assert_formatter_matches_fixture(&comments_formatter);
|
|
assert_formatter_matches_fixture(&enum_basic_formatter);
|
|
assert_formatter_matches_fixture(&enum_payload_direct_scalars_formatter);
|
|
assert_formatter_matches_fixture(&enum_payload_structs_formatter);
|
|
assert_formatter_matches_fixture(&enum_payload_i32_formatter);
|
|
assert_formatter_matches_fixture(&enum_struct_field_formatter);
|
|
assert_formatter_matches_fixture(&formatter_stability_v1);
|
|
assert_formatter_matches_fixture(&checked_i64_to_i32_formatter);
|
|
assert_formatter_matches_fixture(&host_io_formatter);
|
|
assert_formatter_matches_fixture(&integer_bitwise_formatter);
|
|
assert_formatter_matches_fixture(&integer_remainder_formatter);
|
|
assert_formatter_matches_fixture(&integer_to_string_formatter);
|
|
assert_formatter_matches_fixture(&f64_to_string_formatter);
|
|
assert_formatter_matches_fixture(&f64_to_i32_result_formatter);
|
|
assert_formatter_matches_fixture(&f64_to_i64_result_formatter);
|
|
assert_formatter_matches_fixture(&owned_string_concat_formatter);
|
|
assert_formatter_matches_fixture(&print_bool_formatter);
|
|
assert_formatter_matches_fixture(&primitive_struct_fields_formatter);
|
|
assert_formatter_matches_fixture(&random_formatter);
|
|
assert_formatter_matches_fixture(&stdin_result_formatter);
|
|
assert_formatter_matches_fixture(&string_parse_i32_result_formatter);
|
|
assert_formatter_matches_fixture(&string_parse_i64_result_formatter);
|
|
assert_formatter_matches_fixture(&string_parse_f64_result_formatter);
|
|
assert_formatter_matches_fixture(&string_parse_bool_result_formatter);
|
|
assert_formatter_matches_fixture(&numeric_struct_fields_formatter);
|
|
assert_formatter_matches_fixture(&numeric_widening_formatter);
|
|
assert_formatter_matches_fixture(&result_helpers_formatter);
|
|
assert_formatter_matches_fixture(&standard_runtime_formatter);
|
|
assert_formatter_matches_fixture(&time_sleep_formatter);
|
|
assert_formatter_matches_fixture(&string_print_formatter);
|
|
assert_formatter_matches_fixture(&string_value_flow_formatter);
|
|
assert_formatter_matches_fixture(&vec_i32_formatter);
|
|
assert_lowering_inspector_matrix_matches_fixtures(&repo);
|
|
assert_lowering_inspector_matches_fixture(
|
|
&repo,
|
|
&glagol_add,
|
|
"--inspect-lowering=surface",
|
|
"add.surface.lower",
|
|
);
|
|
assert_lowering_inspector_matches_fixture(
|
|
&repo,
|
|
&glagol_add,
|
|
"--inspect-lowering=checked",
|
|
"add.checked.lower",
|
|
);
|
|
assert_top_level_test_tooling_matches_fixtures(&repo);
|
|
assert_array_direct_scalars_tooling_matches_fixtures(
|
|
&glagol_array_direct_scalars,
|
|
&array_direct_scalars_formatter,
|
|
);
|
|
assert_array_direct_scalars_value_flow_tooling_matches_fixtures(
|
|
&glagol_array_direct_scalars_value_flow,
|
|
&array_direct_scalars_value_flow_formatter,
|
|
);
|
|
assert_array_string_tooling_matches_fixtures(&glagol_array_string, &array_string_formatter);
|
|
assert_array_string_value_flow_tooling_matches_fixtures(
|
|
&glagol_array_string_value_flow,
|
|
&array_string_value_flow_formatter,
|
|
);
|
|
assert_array_tooling_matches_fixtures(&glagol_array, &array_formatter);
|
|
assert_array_value_flow_tooling_matches_fixtures(
|
|
&glagol_array_value_flow,
|
|
&array_value_flow_formatter,
|
|
);
|
|
assert_if_tooling_matches_fixtures(&glagol_if, &if_formatter);
|
|
assert_local_variable_tooling_matches_fixtures(&glagol_local, &local_formatter);
|
|
assert_option_result_tooling_matches_fixtures(&glagol_option_result, &option_result_formatter);
|
|
assert_option_result_flow_tooling_matches_fixtures(
|
|
&glagol_option_result_flow,
|
|
&option_result_flow_formatter,
|
|
);
|
|
assert_option_result_match_tooling_matches_fixtures(
|
|
&glagol_option_result_match,
|
|
&option_result_match_formatter,
|
|
);
|
|
assert_option_result_payload_tooling_matches_fixtures(
|
|
&glagol_option_result_payload,
|
|
&option_result_payload_formatter,
|
|
);
|
|
assert_enum_struct_field_tooling_matches_fixtures(
|
|
&glagol_enum_struct_field,
|
|
&enum_struct_field_formatter,
|
|
);
|
|
assert_primitive_struct_field_tooling_matches_fixtures(
|
|
&glagol_primitive_struct_fields,
|
|
&primitive_struct_fields_formatter,
|
|
);
|
|
assert_numeric_struct_field_tooling_matches_fixtures(
|
|
&glagol_numeric_struct_fields,
|
|
&numeric_struct_fields_formatter,
|
|
);
|
|
assert_owned_string_concat_tooling_matches_fixtures(
|
|
&glagol_owned_string_concat,
|
|
&owned_string_concat_formatter,
|
|
);
|
|
assert_print_bool_tooling_matches_fixtures(&glagol_print_bool, &print_bool_formatter);
|
|
assert_random_tooling_matches_fixtures(&glagol_random, &random_formatter);
|
|
assert_stdin_result_tooling_matches_fixtures(&glagol_stdin_result, &stdin_result_formatter);
|
|
assert_string_parse_i32_result_tooling_matches_fixtures(
|
|
&glagol_string_parse_i32_result,
|
|
&string_parse_i32_result_formatter,
|
|
);
|
|
assert_string_parse_i64_result_tooling_matches_fixtures(
|
|
&glagol_string_parse_i64_result,
|
|
&string_parse_i64_result_formatter,
|
|
);
|
|
assert_string_parse_f64_result_tooling_matches_fixtures(
|
|
&glagol_string_parse_f64_result,
|
|
&string_parse_f64_result_formatter,
|
|
);
|
|
assert_string_parse_bool_result_tooling_matches_fixtures(
|
|
&glagol_string_parse_bool_result,
|
|
&string_parse_bool_result_formatter,
|
|
);
|
|
assert_result_f64_bool_source_flow_matches_fixture(&glagol_result_f64_bool_match);
|
|
assert_f64_to_string_tooling_matches_fixtures(&glagol_f64_to_string, &f64_to_string_formatter);
|
|
assert_f64_to_i32_result_tooling_matches_fixtures(
|
|
&glagol_f64_to_i32_result,
|
|
&f64_to_i32_result_formatter,
|
|
);
|
|
assert_f64_to_i64_result_tooling_matches_fixtures(
|
|
&glagol_f64_to_i64_result,
|
|
&f64_to_i64_result_formatter,
|
|
);
|
|
assert_result_helpers_tooling_matches_fixtures(
|
|
&glagol_result_helpers,
|
|
&result_helpers_formatter,
|
|
);
|
|
assert_standard_runtime_tooling_matches_fixtures(
|
|
&glagol_standard_runtime,
|
|
&standard_runtime_formatter,
|
|
);
|
|
assert_time_sleep_tooling_matches_fixtures(&glagol_time_sleep, &time_sleep_formatter);
|
|
assert_string_print_tooling_matches_fixtures(&glagol_string_print, &string_print_formatter);
|
|
assert_string_value_flow_tooling_matches_fixtures(
|
|
&glagol_string_value_flow,
|
|
&string_value_flow_formatter,
|
|
);
|
|
assert_struct_tooling_matches_fixtures(&glagol_struct, &struct_formatter);
|
|
assert_struct_value_flow_tooling_matches_fixtures(
|
|
&glagol_struct_value_flow,
|
|
&struct_value_flow_formatter,
|
|
);
|
|
assert_unsafe_tooling_matches_fixtures(&repo, &glagol_unsafe, &unsafe_formatter);
|
|
assert_vec_i32_tooling_matches_fixtures(&glagol_vec_i32, &vec_i32_formatter);
|
|
assert_while_tooling_matches_fixtures(&glagol_while, &while_formatter);
|
|
assert_project_enum_imports_tooling_matches_fixture(&glagol_project_enum_imports);
|
|
assert_project_std_layout_local_math_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_math,
|
|
);
|
|
assert_project_std_import_math_tooling_matches_fixture(&glagol_project_std_import_math);
|
|
assert_project_std_import_result_tooling_matches_fixture(&glagol_project_std_import_result);
|
|
assert_project_std_import_option_tooling_matches_fixture(&glagol_project_std_import_option);
|
|
assert_project_std_import_time_tooling_matches_fixture(&glagol_project_std_import_time);
|
|
assert_project_std_import_random_tooling_matches_fixture(&glagol_project_std_import_random);
|
|
assert_project_std_import_env_tooling_matches_fixture(&glagol_project_std_import_env);
|
|
assert_project_std_import_fs_tooling_matches_fixture(&glagol_project_std_import_fs);
|
|
assert_project_std_import_net_tooling_matches_fixture(&glagol_project_std_import_net);
|
|
assert_project_std_import_json_tooling_matches_fixture(&glagol_project_std_import_json);
|
|
assert_project_std_import_process_tooling_matches_fixture(&glagol_project_std_import_process);
|
|
assert_project_std_import_string_tooling_matches_fixture(&glagol_project_std_import_string);
|
|
assert_project_std_import_num_tooling_matches_fixture(&glagol_project_std_import_num);
|
|
assert_project_std_import_io_tooling_matches_fixture(&glagol_project_std_import_io);
|
|
assert_project_std_import_cli_tooling_matches_fixture(&glagol_project_std_import_cli);
|
|
assert_project_std_import_vec_i32_tooling_matches_fixture(&glagol_project_std_import_vec_i32);
|
|
assert_project_std_import_vec_i64_tooling_matches_fixture(&glagol_project_std_import_vec_i64);
|
|
assert_project_std_import_vec_f64_tooling_matches_fixture(&glagol_project_std_import_vec_f64);
|
|
assert_project_std_import_vec_bool_tooling_matches_fixture(&glagol_project_std_import_vec_bool);
|
|
assert_project_std_import_vec_string_tooling_matches_fixture(
|
|
&glagol_project_std_import_vec_string,
|
|
);
|
|
assert_workspace_std_import_option_tooling_matches_fixture(&glagol_workspace_std_import_option);
|
|
assert_project_std_layout_local_num_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_num,
|
|
);
|
|
assert_project_std_layout_local_option_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_option,
|
|
);
|
|
assert_project_std_layout_local_process_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_process,
|
|
);
|
|
assert_project_std_layout_local_result_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_result,
|
|
);
|
|
assert_project_std_layout_local_string_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_string,
|
|
);
|
|
assert_project_std_layout_local_time_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_time,
|
|
);
|
|
assert_project_std_layout_local_random_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_random,
|
|
);
|
|
assert_project_std_layout_local_env_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_env,
|
|
);
|
|
assert_project_std_layout_local_fs_tooling_matches_fixture(&glagol_project_std_layout_local_fs);
|
|
assert_project_std_layout_local_net_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_net,
|
|
);
|
|
assert_project_std_layout_local_json_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_json,
|
|
);
|
|
assert_project_std_layout_local_io_tooling_matches_fixture(&glagol_project_std_layout_local_io);
|
|
assert_project_std_layout_local_cli_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_cli,
|
|
);
|
|
assert_project_std_layout_local_vec_i32_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_vec_i32,
|
|
);
|
|
assert_project_std_layout_local_vec_i64_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_vec_i64,
|
|
);
|
|
assert_project_std_layout_local_vec_f64_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_vec_f64,
|
|
);
|
|
assert_project_std_layout_local_vec_bool_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_vec_bool,
|
|
);
|
|
assert_project_std_layout_local_vec_string_tooling_matches_fixture(
|
|
&glagol_project_std_layout_local_vec_string,
|
|
);
|
|
assert_math_loop_benchmark_scaffold_is_promotable(&glagol_benchmark_math_loop);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_branch_loop,
|
|
"branch-loop",
|
|
"branch_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_parse_loop,
|
|
"parse-loop",
|
|
"parse_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_json_quote_loop,
|
|
"json-quote-loop",
|
|
"json_quote_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_array_index_loop,
|
|
"array-index-loop",
|
|
"array_index_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_string_eq_loop,
|
|
"string-eq-loop",
|
|
"string_eq_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_array_struct_field_loop,
|
|
"array-struct-field-loop",
|
|
"array_struct_field_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_enum_struct_payload_loop,
|
|
"enum-struct-payload-loop",
|
|
"enum_struct_payload_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_vec_i32_index_loop,
|
|
"vec-i32-index-loop",
|
|
"vec_i32_index_loop",
|
|
);
|
|
assert_named_benchmark_scaffold_is_promotable(
|
|
&glagol_benchmark_vec_string_eq_loop,
|
|
"vec-string-eq-loop",
|
|
"vec_string_eq_loop",
|
|
);
|
|
assert_installed_standard_library_discovery_is_promotable(&repo);
|
|
assert_diagnostic_snapshots_are_promotable(&repo);
|
|
}
|
|
|
|
#[test]
|
|
#[ignore = "requires a Slovo monorepo checkout; default glagol tests stay standalone"]
|
|
fn hermeticum_slovo_fixture_alignment_is_preserved() {
|
|
let repo = repo_root();
|
|
let slovo_supported_add = repo.join("docs/language/examples/supported/add.slo");
|
|
let slovo_supported_array_direct_scalars =
|
|
repo.join("docs/language/examples/supported/array-direct-scalars.slo");
|
|
let slovo_supported_array_direct_scalars_value_flow =
|
|
repo.join("docs/language/examples/supported/array-direct-scalars-value-flow.slo");
|
|
let slovo_supported_array_enum = repo.join("docs/language/examples/supported/array-enum.slo");
|
|
let slovo_supported_array_string =
|
|
repo.join("docs/language/examples/supported/array-string.slo");
|
|
let slovo_supported_array_string_value_flow =
|
|
repo.join("docs/language/examples/supported/array-string-value-flow.slo");
|
|
let slovo_supported_array_struct_elements =
|
|
repo.join("docs/language/examples/supported/array-struct-elements.slo");
|
|
let slovo_supported_array = repo.join("docs/language/examples/supported/array.slo");
|
|
let slovo_supported_array_value_flow =
|
|
repo.join("docs/language/examples/supported/array-value-flow.slo");
|
|
let slovo_supported_boolean_logic =
|
|
repo.join("docs/language/examples/supported/boolean-logic.slo");
|
|
let slovo_supported_checked_i64_to_i32 =
|
|
repo.join("docs/language/examples/supported/checked-i64-to-i32-conversion.slo");
|
|
let slovo_supported_enum_basic = repo.join("docs/language/examples/supported/enum-basic.slo");
|
|
let slovo_supported_enum_payload_direct_scalars =
|
|
repo.join("docs/language/examples/supported/enum-payload-direct-scalars.slo");
|
|
let slovo_supported_enum_payload_structs =
|
|
repo.join("docs/language/examples/supported/enum-payload-structs.slo");
|
|
let slovo_supported_enum_payload_i32 =
|
|
repo.join("docs/language/examples/supported/enum-payload-i32.slo");
|
|
let slovo_supported_enum_struct_fields =
|
|
repo.join("docs/language/examples/supported/enum-struct-fields.slo");
|
|
let slovo_supported_host_io = repo.join("docs/language/examples/supported/host-io.slo");
|
|
let slovo_supported_host_io_result =
|
|
repo.join("docs/language/examples/supported/host-io-result.slo");
|
|
let slovo_supported_if = repo.join("docs/language/examples/supported/if.slo");
|
|
let slovo_supported_integer_bitwise =
|
|
repo.join("docs/language/examples/supported/integer-bitwise.slo");
|
|
let slovo_supported_integer_remainder =
|
|
repo.join("docs/language/examples/supported/integer-remainder.slo");
|
|
let slovo_supported_integer_to_string =
|
|
repo.join("docs/language/examples/supported/integer-to-string.slo");
|
|
let slovo_supported_f64_to_string =
|
|
repo.join("docs/language/examples/supported/f64-to-string.slo");
|
|
let slovo_supported_f64_to_i32_result =
|
|
repo.join("docs/language/examples/supported/f64-to-i32-result.slo");
|
|
let slovo_supported_f64_to_i64_result =
|
|
repo.join("docs/language/examples/supported/f64-to-i64-result.slo");
|
|
let slovo_supported_composite =
|
|
repo.join("docs/language/examples/supported/composite-locals.slo");
|
|
let slovo_supported_composite_struct_fields =
|
|
repo.join("docs/language/examples/supported/composite-struct-fields.slo");
|
|
let slovo_supported_test = repo.join("docs/language/examples/supported/top-level-test.slo");
|
|
let slovo_supported_local = repo.join("docs/language/examples/supported/local-variables.slo");
|
|
let slovo_supported_numeric_struct_fields =
|
|
repo.join("docs/language/examples/supported/numeric-struct-fields.slo");
|
|
let slovo_supported_numeric_widening =
|
|
repo.join("docs/language/examples/supported/numeric-widening-conversions.slo");
|
|
let slovo_supported_option_result =
|
|
repo.join("docs/language/examples/supported/option-result.slo");
|
|
let slovo_supported_option_result_flow =
|
|
repo.join("docs/language/examples/supported/option-result-flow.slo");
|
|
let slovo_supported_option_result_match =
|
|
repo.join("docs/language/examples/supported/option-result-match.slo");
|
|
let slovo_supported_option_result_payload =
|
|
repo.join("docs/language/examples/supported/option-result-payload.slo");
|
|
let slovo_supported_owned_string_concat =
|
|
repo.join("docs/language/examples/supported/owned-string-concat.slo");
|
|
let slovo_supported_print_bool = repo.join("docs/language/examples/supported/print-bool.slo");
|
|
let slovo_supported_primitive_struct_fields =
|
|
repo.join("docs/language/examples/supported/primitive-struct-fields.slo");
|
|
let slovo_supported_random = repo.join("docs/language/examples/supported/random.slo");
|
|
let slovo_supported_stdin_result =
|
|
repo.join("docs/language/examples/supported/stdin-result.slo");
|
|
let slovo_supported_string_parse_i32_result =
|
|
repo.join("docs/language/examples/supported/string-parse-i32-result.slo");
|
|
let slovo_supported_string_parse_i64_result =
|
|
repo.join("docs/language/examples/supported/string-parse-i64-result.slo");
|
|
let slovo_supported_string_parse_bool_result =
|
|
repo.join("docs/language/examples/supported/string-parse-bool-result.slo");
|
|
let slovo_supported_result_helpers =
|
|
repo.join("docs/language/examples/supported/result-helpers.slo");
|
|
let slovo_supported_result_f64_bool_match =
|
|
repo.join("docs/language/examples/supported/result-f64-bool-match.slo");
|
|
let slovo_supported_standard_runtime =
|
|
repo.join("docs/language/examples/supported/standard-runtime.slo");
|
|
let slovo_supported_time_sleep = repo.join("docs/language/examples/supported/time-sleep.slo");
|
|
let slovo_supported_string_print =
|
|
repo.join("docs/language/examples/supported/string-print.slo");
|
|
let slovo_supported_string_value_flow =
|
|
repo.join("docs/language/examples/supported/string-value-flow.slo");
|
|
let slovo_supported_struct = repo.join("docs/language/examples/supported/struct.slo");
|
|
let slovo_supported_struct_value_flow =
|
|
repo.join("docs/language/examples/supported/struct-value-flow.slo");
|
|
let slovo_supported_unsafe = repo.join("docs/language/examples/supported/unsafe.slo");
|
|
let slovo_supported_vec_i32 = repo.join("docs/language/examples/supported/vec-i32.slo");
|
|
let slovo_supported_vec_f64 = repo.join("docs/language/examples/supported/vec-f64.slo");
|
|
let slovo_supported_vec_bool = repo.join("docs/language/examples/supported/vec-bool.slo");
|
|
let slovo_supported_vec_string = repo.join("docs/language/examples/supported/vec-string.slo");
|
|
let slovo_supported_while = repo.join("docs/language/examples/supported/while.slo");
|
|
let slovo_project_enum_imports_manifest =
|
|
repo.join("docs/language/examples/projects/enum-imports/slovo.toml");
|
|
let slovo_project_enum_imports_readings =
|
|
repo.join("docs/language/examples/projects/enum-imports/src/readings.slo");
|
|
let slovo_project_enum_imports_main =
|
|
repo.join("docs/language/examples/projects/enum-imports/src/main.slo");
|
|
let slovo_project_std_import_time_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-time/slovo.toml");
|
|
let slovo_project_std_import_time_main =
|
|
repo.join("docs/language/examples/projects/std-import-time/src/main.slo");
|
|
let slovo_project_std_import_random_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-random/slovo.toml");
|
|
let slovo_project_std_import_random_main =
|
|
repo.join("docs/language/examples/projects/std-import-random/src/main.slo");
|
|
let slovo_project_std_import_env_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-env/slovo.toml");
|
|
let slovo_project_std_import_env_main =
|
|
repo.join("docs/language/examples/projects/std-import-env/src/main.slo");
|
|
let slovo_project_std_import_fs_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-fs/slovo.toml");
|
|
let slovo_project_std_import_fs_main =
|
|
repo.join("docs/language/examples/projects/std-import-fs/src/main.slo");
|
|
let slovo_project_std_import_process_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-process/slovo.toml");
|
|
let slovo_project_std_import_process_main =
|
|
repo.join("docs/language/examples/projects/std-import-process/src/main.slo");
|
|
let slovo_project_std_import_string_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-string/slovo.toml");
|
|
let slovo_project_std_import_string_main =
|
|
repo.join("docs/language/examples/projects/std-import-string/src/main.slo");
|
|
let slovo_project_std_import_num_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-num/slovo.toml");
|
|
let slovo_project_std_import_num_main =
|
|
repo.join("docs/language/examples/projects/std-import-num/src/main.slo");
|
|
let slovo_project_std_import_io_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-io/slovo.toml");
|
|
let slovo_project_std_import_io_main =
|
|
repo.join("docs/language/examples/projects/std-import-io/src/main.slo");
|
|
let slovo_project_std_import_cli_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-cli/slovo.toml");
|
|
let slovo_project_std_import_cli_main =
|
|
repo.join("docs/language/examples/projects/std-import-cli/src/main.slo");
|
|
let slovo_project_std_import_vec_i32_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-vec_i32/slovo.toml");
|
|
let slovo_project_std_import_vec_i32_main =
|
|
repo.join("docs/language/examples/projects/std-import-vec_i32/src/main.slo");
|
|
let slovo_project_std_import_vec_f64_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-vec_f64/slovo.toml");
|
|
let slovo_project_std_import_vec_f64_main =
|
|
repo.join("docs/language/examples/projects/std-import-vec_f64/src/main.slo");
|
|
let slovo_project_std_import_vec_bool_manifest =
|
|
repo.join("docs/language/examples/projects/std-import-vec_bool/slovo.toml");
|
|
let slovo_project_std_import_vec_bool_main =
|
|
repo.join("docs/language/examples/projects/std-import-vec_bool/src/main.slo");
|
|
let slovo_formatter_canonical = repo.join("docs/language/examples/formatter/canonical.slo");
|
|
let slovo_formatter_array_direct_scalars =
|
|
repo.join("docs/language/examples/formatter/array-direct-scalars.slo");
|
|
let slovo_formatter_array_direct_scalars_value_flow =
|
|
repo.join("docs/language/examples/formatter/array-direct-scalars-value-flow.slo");
|
|
let slovo_formatter_array_enum = repo.join("docs/language/examples/formatter/array-enum.slo");
|
|
let slovo_formatter_array_string =
|
|
repo.join("docs/language/examples/formatter/array-string.slo");
|
|
let slovo_formatter_array_string_value_flow =
|
|
repo.join("docs/language/examples/formatter/array-string-value-flow.slo");
|
|
let slovo_formatter_array_struct_elements =
|
|
repo.join("docs/language/examples/formatter/array-struct-elements.slo");
|
|
let slovo_formatter_array = repo.join("docs/language/examples/formatter/array.slo");
|
|
let slovo_formatter_array_value_flow =
|
|
repo.join("docs/language/examples/formatter/array-value-flow.slo");
|
|
let slovo_formatter_boolean_logic =
|
|
repo.join("docs/language/examples/formatter/boolean-logic.slo");
|
|
let slovo_formatter_checked_i64_to_i32 =
|
|
repo.join("docs/language/examples/formatter/checked-i64-to-i32-conversion.slo");
|
|
let slovo_formatter_comments = repo.join("docs/language/examples/formatter/comments.slo");
|
|
let slovo_formatter_enum_payload_direct_scalars =
|
|
repo.join("docs/language/examples/formatter/enum-payload-direct-scalars.slo");
|
|
let slovo_formatter_enum_payload_structs =
|
|
repo.join("docs/language/examples/formatter/enum-payload-structs.slo");
|
|
let slovo_formatter_enum_payload_i32 =
|
|
repo.join("docs/language/examples/formatter/enum-payload-i32.slo");
|
|
let slovo_formatter_enum_struct_fields =
|
|
repo.join("docs/language/examples/formatter/enum-struct-fields.slo");
|
|
let slovo_formatter_host_io = repo.join("docs/language/examples/formatter/host-io.slo");
|
|
let slovo_formatter_host_io_result =
|
|
repo.join("docs/language/examples/formatter/host-io-result.slo");
|
|
let slovo_formatter_if = repo.join("docs/language/examples/formatter/if.slo");
|
|
let slovo_formatter_integer_bitwise =
|
|
repo.join("docs/language/examples/formatter/integer-bitwise.slo");
|
|
let slovo_formatter_integer_remainder =
|
|
repo.join("docs/language/examples/formatter/integer-remainder.slo");
|
|
let slovo_formatter_integer_to_string =
|
|
repo.join("docs/language/examples/formatter/integer-to-string.slo");
|
|
let slovo_formatter_f64_to_string =
|
|
repo.join("docs/language/examples/formatter/f64-to-string.slo");
|
|
let slovo_formatter_f64_to_i32_result =
|
|
repo.join("docs/language/examples/formatter/f64-to-i32-result.slo");
|
|
let slovo_formatter_f64_to_i64_result =
|
|
repo.join("docs/language/examples/formatter/f64-to-i64-result.slo");
|
|
let slovo_formatter_composite =
|
|
repo.join("docs/language/examples/formatter/composite-locals.slo");
|
|
let slovo_formatter_composite_struct_fields =
|
|
repo.join("docs/language/examples/formatter/composite-struct-fields.slo");
|
|
let slovo_formatter_test = repo.join("docs/language/examples/formatter/top-level-test.slo");
|
|
let slovo_formatter_local = repo.join("docs/language/examples/formatter/local-variables.slo");
|
|
let slovo_formatter_numeric_struct_fields =
|
|
repo.join("docs/language/examples/formatter/numeric-struct-fields.slo");
|
|
let slovo_formatter_numeric_widening =
|
|
repo.join("docs/language/examples/formatter/numeric-widening-conversions.slo");
|
|
let slovo_formatter_option_result =
|
|
repo.join("docs/language/examples/formatter/option-result.slo");
|
|
let slovo_formatter_option_result_flow =
|
|
repo.join("docs/language/examples/formatter/option-result-flow.slo");
|
|
let slovo_formatter_option_result_match =
|
|
repo.join("docs/language/examples/formatter/option-result-match.slo");
|
|
let slovo_formatter_option_result_payload =
|
|
repo.join("docs/language/examples/formatter/option-result-payload.slo");
|
|
let slovo_formatter_owned_string_concat =
|
|
repo.join("docs/language/examples/formatter/owned-string-concat.slo");
|
|
let slovo_formatter_print_bool = repo.join("docs/language/examples/formatter/print-bool.slo");
|
|
let slovo_formatter_primitive_struct_fields =
|
|
repo.join("docs/language/examples/formatter/primitive-struct-fields.slo");
|
|
let slovo_formatter_random = repo.join("docs/language/examples/formatter/random.slo");
|
|
let slovo_formatter_stdin_result =
|
|
repo.join("docs/language/examples/formatter/stdin-result.slo");
|
|
let slovo_formatter_string_parse_i32_result =
|
|
repo.join("docs/language/examples/formatter/string-parse-i32-result.slo");
|
|
let slovo_formatter_string_parse_i64_result =
|
|
repo.join("docs/language/examples/formatter/string-parse-i64-result.slo");
|
|
let slovo_formatter_string_parse_bool_result =
|
|
repo.join("docs/language/examples/formatter/string-parse-bool-result.slo");
|
|
let slovo_formatter_result_helpers =
|
|
repo.join("docs/language/examples/formatter/result-helpers.slo");
|
|
let slovo_formatter_standard_runtime =
|
|
repo.join("docs/language/examples/formatter/standard-runtime.slo");
|
|
let slovo_formatter_time_sleep = repo.join("docs/language/examples/formatter/time-sleep.slo");
|
|
let slovo_formatter_string_print =
|
|
repo.join("docs/language/examples/formatter/string-print.slo");
|
|
let slovo_formatter_string_value_flow =
|
|
repo.join("docs/language/examples/formatter/string-value-flow.slo");
|
|
let slovo_formatter_struct = repo.join("docs/language/examples/formatter/struct.slo");
|
|
let slovo_formatter_struct_value_flow =
|
|
repo.join("docs/language/examples/formatter/struct-value-flow.slo");
|
|
let slovo_formatter_unsafe = repo.join("docs/language/examples/formatter/unsafe.slo");
|
|
let slovo_formatter_vec_i32 = repo.join("docs/language/examples/formatter/vec-i32.slo");
|
|
let slovo_formatter_vec_f64 = repo.join("docs/language/examples/formatter/vec-f64.slo");
|
|
let slovo_formatter_vec_bool = repo.join("docs/language/examples/formatter/vec-bool.slo");
|
|
let slovo_formatter_while = repo.join("docs/language/examples/formatter/while.slo");
|
|
let glagol_add = repo.join("examples/add.slo");
|
|
let glagol_array_direct_scalars = repo.join("examples/array-direct-scalars.slo");
|
|
let glagol_array_direct_scalars_value_flow =
|
|
repo.join("examples/array-direct-scalars-value-flow.slo");
|
|
let glagol_array_enum = repo.join("examples/array-enum.slo");
|
|
let glagol_array_string = repo.join("examples/array-string.slo");
|
|
let glagol_array_string_value_flow = repo.join("examples/array-string-value-flow.slo");
|
|
let glagol_array_struct_elements = repo.join("examples/array-struct-elements.slo");
|
|
let glagol_array = repo.join("examples/array.slo");
|
|
let glagol_array_value_flow = repo.join("examples/array-value-flow.slo");
|
|
let glagol_boolean_logic = repo.join("examples/boolean-logic.slo");
|
|
let glagol_checked_i64_to_i32 = repo.join("examples/checked-i64-to-i32-conversion.slo");
|
|
let glagol_enum_basic = repo.join("examples/enum-basic.slo");
|
|
let glagol_enum_payload_direct_scalars = repo.join("examples/enum-payload-direct-scalars.slo");
|
|
let glagol_enum_payload_structs = repo.join("examples/enum-payload-structs.slo");
|
|
let glagol_enum_payload_i32 = repo.join("examples/enum-payload-i32.slo");
|
|
let glagol_enum_struct_fields = repo.join("examples/enum-struct-fields.slo");
|
|
let glagol_host_io = repo.join("examples/host-io.slo");
|
|
let glagol_host_io_result = repo.join("examples/host-io-result.slo");
|
|
let glagol_if = repo.join("examples/if.slo");
|
|
let glagol_integer_bitwise = repo.join("examples/integer-bitwise.slo");
|
|
let glagol_integer_remainder = repo.join("examples/integer-remainder.slo");
|
|
let glagol_integer_to_string = repo.join("examples/integer-to-string.slo");
|
|
let glagol_f64_to_string = repo.join("examples/f64-to-string.slo");
|
|
let glagol_f64_to_i32_result = repo.join("examples/f64-to-i32-result.slo");
|
|
let glagol_f64_to_i64_result = repo.join("examples/f64-to-i64-result.slo");
|
|
let glagol_composite = repo.join("examples/composite-locals.slo");
|
|
let glagol_composite_struct_fields = repo.join("examples/composite-struct-fields.slo");
|
|
let glagol_local = repo.join("examples/local-variables.slo");
|
|
let glagol_numeric_struct_fields = repo.join("examples/numeric-struct-fields.slo");
|
|
let glagol_numeric_widening = repo.join("examples/numeric-widening-conversions.slo");
|
|
let glagol_option_result = repo.join("examples/option-result.slo");
|
|
let glagol_option_result_flow = repo.join("examples/option-result-flow.slo");
|
|
let glagol_option_result_match = repo.join("examples/option-result-match.slo");
|
|
let glagol_option_result_payload = repo.join("examples/option-result-payload.slo");
|
|
let glagol_owned_string_concat = repo.join("examples/owned-string-concat.slo");
|
|
let glagol_print_bool = repo.join("examples/print-bool.slo");
|
|
let glagol_primitive_struct_fields = repo.join("examples/primitive-struct-fields.slo");
|
|
let glagol_random = repo.join("examples/random.slo");
|
|
let glagol_stdin_result = repo.join("examples/stdin-result.slo");
|
|
let glagol_string_parse_i32_result = repo.join("examples/string-parse-i32-result.slo");
|
|
let glagol_string_parse_i64_result = repo.join("examples/string-parse-i64-result.slo");
|
|
let glagol_string_parse_bool_result = repo.join("examples/string-parse-bool-result.slo");
|
|
let glagol_result_helpers = repo.join("examples/result-helpers.slo");
|
|
let glagol_result_f64_bool_match = repo.join("examples/result-f64-bool-match.slo");
|
|
let glagol_standard_runtime = repo.join("examples/standard-runtime.slo");
|
|
let glagol_time_sleep = repo.join("examples/time-sleep.slo");
|
|
let glagol_string_print = repo.join("examples/string-print.slo");
|
|
let glagol_string_value_flow = repo.join("examples/string-value-flow.slo");
|
|
let glagol_struct = repo.join("examples/struct.slo");
|
|
let glagol_struct_value_flow = repo.join("examples/struct-value-flow.slo");
|
|
let glagol_unsafe = repo.join("examples/unsafe.slo");
|
|
let glagol_vec_i32 = repo.join("examples/vec-i32.slo");
|
|
let glagol_vec_f64 = repo.join("examples/vec-f64.slo");
|
|
let glagol_vec_bool = repo.join("examples/vec-bool.slo");
|
|
let glagol_vec_string = repo.join("examples/vec-string.slo");
|
|
let glagol_while = repo.join("examples/while.slo");
|
|
let glagol_project_enum_imports_manifest =
|
|
repo.join("examples/projects/enum-imports/slovo.toml");
|
|
let glagol_project_enum_imports_readings =
|
|
repo.join("examples/projects/enum-imports/src/readings.slo");
|
|
let glagol_project_enum_imports_main = repo.join("examples/projects/enum-imports/src/main.slo");
|
|
let glagol_project_std_layout_local_math_manifest =
|
|
repo.join("examples/projects/std-layout-local-math/slovo.toml");
|
|
let glagol_project_std_layout_local_math_math =
|
|
repo.join("examples/projects/std-layout-local-math/src/math.slo");
|
|
let glagol_project_std_layout_local_math_main =
|
|
repo.join("examples/projects/std-layout-local-math/src/main.slo");
|
|
let glagol_project_std_layout_local_num_manifest =
|
|
repo.join("examples/projects/std-layout-local-num/slovo.toml");
|
|
let glagol_project_std_layout_local_num_num =
|
|
repo.join("examples/projects/std-layout-local-num/src/num.slo");
|
|
let glagol_project_std_layout_local_num_main =
|
|
repo.join("examples/projects/std-layout-local-num/src/main.slo");
|
|
let glagol_project_std_layout_local_process_manifest =
|
|
repo.join("examples/projects/std-layout-local-process/slovo.toml");
|
|
let glagol_project_std_layout_local_process_process =
|
|
repo.join("examples/projects/std-layout-local-process/src/process.slo");
|
|
let glagol_project_std_layout_local_process_main =
|
|
repo.join("examples/projects/std-layout-local-process/src/main.slo");
|
|
let glagol_project_std_layout_local_result_manifest =
|
|
repo.join("examples/projects/std-layout-local-result/slovo.toml");
|
|
let glagol_project_std_layout_local_result_result =
|
|
repo.join("examples/projects/std-layout-local-result/src/result.slo");
|
|
let glagol_project_std_layout_local_result_main =
|
|
repo.join("examples/projects/std-layout-local-result/src/main.slo");
|
|
let glagol_project_std_layout_local_string_manifest =
|
|
repo.join("examples/projects/std-layout-local-string/slovo.toml");
|
|
let glagol_project_std_layout_local_string_string =
|
|
repo.join("examples/projects/std-layout-local-string/src/string.slo");
|
|
let glagol_project_std_layout_local_string_main =
|
|
repo.join("examples/projects/std-layout-local-string/src/main.slo");
|
|
let glagol_project_std_layout_local_cli_manifest =
|
|
repo.join("examples/projects/std-layout-local-cli/slovo.toml");
|
|
let glagol_project_std_layout_local_cli_cli =
|
|
repo.join("examples/projects/std-layout-local-cli/src/cli.slo");
|
|
let glagol_project_std_layout_local_cli_process =
|
|
repo.join("examples/projects/std-layout-local-cli/src/process.slo");
|
|
let glagol_project_std_layout_local_cli_string =
|
|
repo.join("examples/projects/std-layout-local-cli/src/string.slo");
|
|
let glagol_project_std_layout_local_cli_main =
|
|
repo.join("examples/projects/std-layout-local-cli/src/main.slo");
|
|
let glagol_project_std_layout_local_vec_i32_manifest =
|
|
repo.join("examples/projects/std-layout-local-vec_i32/slovo.toml");
|
|
let glagol_project_std_layout_local_vec_i32_vec_i32 =
|
|
repo.join("examples/projects/std-layout-local-vec_i32/src/vec_i32.slo");
|
|
let glagol_project_std_layout_local_vec_i32_main =
|
|
repo.join("examples/projects/std-layout-local-vec_i32/src/main.slo");
|
|
let glagol_project_std_import_time_manifest =
|
|
repo.join("examples/projects/std-import-time/slovo.toml");
|
|
let glagol_project_std_import_time_main =
|
|
repo.join("examples/projects/std-import-time/src/main.slo");
|
|
let glagol_project_std_import_random_manifest =
|
|
repo.join("examples/projects/std-import-random/slovo.toml");
|
|
let glagol_project_std_import_random_main =
|
|
repo.join("examples/projects/std-import-random/src/main.slo");
|
|
let glagol_project_std_import_env_manifest =
|
|
repo.join("examples/projects/std-import-env/slovo.toml");
|
|
let glagol_project_std_import_env_main =
|
|
repo.join("examples/projects/std-import-env/src/main.slo");
|
|
let glagol_project_std_import_fs_manifest =
|
|
repo.join("examples/projects/std-import-fs/slovo.toml");
|
|
let glagol_project_std_import_fs_main =
|
|
repo.join("examples/projects/std-import-fs/src/main.slo");
|
|
let glagol_project_std_import_process_manifest =
|
|
repo.join("examples/projects/std-import-process/slovo.toml");
|
|
let glagol_project_std_import_process_main =
|
|
repo.join("examples/projects/std-import-process/src/main.slo");
|
|
let glagol_project_std_import_string_manifest =
|
|
repo.join("examples/projects/std-import-string/slovo.toml");
|
|
let glagol_project_std_import_string_main =
|
|
repo.join("examples/projects/std-import-string/src/main.slo");
|
|
let glagol_project_std_import_num_manifest =
|
|
repo.join("examples/projects/std-import-num/slovo.toml");
|
|
let glagol_project_std_import_num_main =
|
|
repo.join("examples/projects/std-import-num/src/main.slo");
|
|
let glagol_project_std_import_io_manifest =
|
|
repo.join("examples/projects/std-import-io/slovo.toml");
|
|
let glagol_project_std_import_io_main =
|
|
repo.join("examples/projects/std-import-io/src/main.slo");
|
|
let glagol_project_std_import_cli_manifest =
|
|
repo.join("examples/projects/std-import-cli/slovo.toml");
|
|
let glagol_project_std_import_cli_main =
|
|
repo.join("examples/projects/std-import-cli/src/main.slo");
|
|
let glagol_project_std_import_vec_i32_manifest =
|
|
repo.join("examples/projects/std-import-vec_i32/slovo.toml");
|
|
let glagol_project_std_import_vec_i32_main =
|
|
repo.join("examples/projects/std-import-vec_i32/src/main.slo");
|
|
let glagol_project_std_import_vec_f64_manifest =
|
|
repo.join("examples/projects/std-import-vec_f64/slovo.toml");
|
|
let glagol_project_std_import_vec_f64_main =
|
|
repo.join("examples/projects/std-import-vec_f64/src/main.slo");
|
|
let glagol_project_std_import_vec_bool_manifest =
|
|
repo.join("examples/projects/std-import-vec_bool/slovo.toml");
|
|
let glagol_project_std_import_vec_bool_main =
|
|
repo.join("examples/projects/std-import-vec_bool/src/main.slo");
|
|
let glagol_test = repo.join("tests/top-level-test.slo");
|
|
let glagol_formatter_canonical = repo.join("tests/canonical.fmt");
|
|
let glagol_formatter_array_direct_scalars = repo.join("tests/array-direct-scalars.slo");
|
|
let glagol_formatter_array_direct_scalars_value_flow =
|
|
repo.join("tests/array-direct-scalars-value-flow.slo");
|
|
let glagol_formatter_array_enum = repo.join("tests/array-enum.slo");
|
|
let glagol_formatter_array_string = repo.join("tests/array-string.slo");
|
|
let glagol_formatter_array_string_value_flow = repo.join("tests/array-string-value-flow.slo");
|
|
let glagol_formatter_array_struct_elements = repo.join("tests/array-struct-elements.slo");
|
|
let glagol_formatter_array = repo.join("tests/array.slo");
|
|
let glagol_formatter_array_value_flow = repo.join("tests/array-value-flow.slo");
|
|
let glagol_formatter_boolean_logic = repo.join("tests/boolean-logic.slo");
|
|
let glagol_formatter_checked_i64_to_i32 = repo.join("tests/checked-i64-to-i32-conversion.slo");
|
|
let glagol_formatter_comments = repo.join("tests/comments.slo");
|
|
let glagol_formatter_enum_payload_direct_scalars =
|
|
repo.join("tests/enum-payload-direct-scalars.slo");
|
|
let glagol_formatter_enum_payload_structs = repo.join("tests/enum-payload-structs.slo");
|
|
let glagol_formatter_enum_payload_i32 = repo.join("tests/enum-payload-i32.slo");
|
|
let glagol_formatter_enum_struct_fields = repo.join("tests/enum-struct-fields.slo");
|
|
let glagol_formatter_host_io = repo.join("tests/host-io.slo");
|
|
let glagol_formatter_host_io_result = repo.join("tests/host-io-result.slo");
|
|
let glagol_formatter_if = repo.join("tests/if.slo");
|
|
let glagol_formatter_integer_bitwise = repo.join("tests/integer-bitwise.slo");
|
|
let glagol_formatter_integer_remainder = repo.join("tests/integer-remainder.slo");
|
|
let glagol_formatter_integer_to_string = repo.join("tests/integer-to-string.slo");
|
|
let glagol_formatter_f64_to_string = repo.join("tests/f64-to-string.slo");
|
|
let glagol_formatter_f64_to_i32_result = repo.join("tests/f64-to-i32-result.slo");
|
|
let glagol_formatter_f64_to_i64_result = repo.join("tests/f64-to-i64-result.slo");
|
|
let glagol_formatter_composite = repo.join("tests/composite-locals.slo");
|
|
let glagol_formatter_composite_struct_fields = repo.join("tests/composite-struct-fields.slo");
|
|
let glagol_formatter_test = repo.join("tests/top-level-test.fmt");
|
|
let glagol_formatter_local = repo.join("tests/local-variables.slo");
|
|
let glagol_formatter_numeric_struct_fields = repo.join("tests/numeric-struct-fields.slo");
|
|
let glagol_formatter_numeric_widening = repo.join("tests/numeric-widening-conversions.slo");
|
|
let glagol_formatter_option_result = repo.join("tests/option-result.slo");
|
|
let glagol_formatter_option_result_flow = repo.join("tests/option-result-flow.slo");
|
|
let glagol_formatter_option_result_match = repo.join("tests/option-result-match.slo");
|
|
let glagol_formatter_option_result_payload = repo.join("tests/option-result-payload.slo");
|
|
let glagol_formatter_owned_string_concat = repo.join("tests/owned-string-concat.slo");
|
|
let glagol_formatter_print_bool = repo.join("tests/print-bool.slo");
|
|
let glagol_formatter_primitive_struct_fields = repo.join("tests/primitive-struct-fields.slo");
|
|
let glagol_formatter_random = repo.join("tests/random.slo");
|
|
let glagol_formatter_stdin_result = repo.join("tests/stdin-result.slo");
|
|
let glagol_formatter_string_parse_i32_result = repo.join("tests/string-parse-i32-result.slo");
|
|
let glagol_formatter_string_parse_i64_result = repo.join("tests/string-parse-i64-result.slo");
|
|
let glagol_formatter_string_parse_bool_result = repo.join("tests/string-parse-bool-result.slo");
|
|
let glagol_formatter_result_helpers = repo.join("tests/result-helpers.slo");
|
|
let glagol_formatter_standard_runtime = repo.join("tests/standard-runtime.slo");
|
|
let glagol_formatter_time_sleep = repo.join("tests/time-sleep.slo");
|
|
let glagol_formatter_string_print = repo.join("tests/string-print.slo");
|
|
let glagol_formatter_string_value_flow = repo.join("tests/string-value-flow.slo");
|
|
let glagol_formatter_struct = repo.join("tests/struct.slo");
|
|
let glagol_formatter_struct_value_flow = repo.join("tests/struct-value-flow.slo");
|
|
let glagol_formatter_unsafe = repo.join("tests/unsafe.slo");
|
|
let glagol_formatter_vec_i32 = repo.join("tests/vec-i32.slo");
|
|
let glagol_formatter_while = repo.join("tests/while.slo");
|
|
|
|
assert_slovo_supported_fixtures(&repo);
|
|
assert_slovo_formatter_fixtures(&repo);
|
|
assert_slovo_v0_compatibility_fixtures(&repo);
|
|
assert_source_eq(&glagol_add, &slovo_supported_add);
|
|
assert_source_eq(
|
|
&glagol_array_direct_scalars,
|
|
&slovo_supported_array_direct_scalars,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_array_direct_scalars_value_flow,
|
|
&slovo_supported_array_direct_scalars_value_flow,
|
|
);
|
|
assert_source_eq(&glagol_array_enum, &slovo_supported_array_enum);
|
|
assert_source_eq(&glagol_array_string, &slovo_supported_array_string);
|
|
assert_source_eq(
|
|
&glagol_array_string_value_flow,
|
|
&slovo_supported_array_string_value_flow,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_array_struct_elements,
|
|
&slovo_supported_array_struct_elements,
|
|
);
|
|
assert_source_eq(&glagol_array, &slovo_supported_array);
|
|
assert_source_eq(&glagol_array_value_flow, &slovo_supported_array_value_flow);
|
|
assert_source_eq(&glagol_boolean_logic, &slovo_supported_boolean_logic);
|
|
assert_source_eq(
|
|
&glagol_checked_i64_to_i32,
|
|
&slovo_supported_checked_i64_to_i32,
|
|
);
|
|
assert_source_eq(&glagol_enum_basic, &slovo_supported_enum_basic);
|
|
assert_source_eq(
|
|
&glagol_enum_payload_direct_scalars,
|
|
&slovo_supported_enum_payload_direct_scalars,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_enum_payload_structs,
|
|
&slovo_supported_enum_payload_structs,
|
|
);
|
|
assert_source_eq(&glagol_enum_payload_i32, &slovo_supported_enum_payload_i32);
|
|
assert_source_eq(
|
|
&glagol_enum_struct_fields,
|
|
&slovo_supported_enum_struct_fields,
|
|
);
|
|
assert_source_eq(&glagol_host_io, &slovo_supported_host_io);
|
|
assert_source_eq(&glagol_host_io_result, &slovo_supported_host_io_result);
|
|
assert_source_eq(&glagol_if, &slovo_supported_if);
|
|
assert_source_eq(&glagol_integer_bitwise, &slovo_supported_integer_bitwise);
|
|
assert_source_eq(
|
|
&glagol_integer_remainder,
|
|
&slovo_supported_integer_remainder,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_integer_to_string,
|
|
&slovo_supported_integer_to_string,
|
|
);
|
|
assert_source_eq(&glagol_f64_to_string, &slovo_supported_f64_to_string);
|
|
assert_source_eq(
|
|
&glagol_f64_to_i32_result,
|
|
&slovo_supported_f64_to_i32_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_f64_to_i64_result,
|
|
&slovo_supported_f64_to_i64_result,
|
|
);
|
|
assert_source_eq(&glagol_composite, &slovo_supported_composite);
|
|
assert_source_eq(
|
|
&glagol_composite_struct_fields,
|
|
&slovo_supported_composite_struct_fields,
|
|
);
|
|
assert_source_eq(&glagol_test, &slovo_supported_test);
|
|
assert_source_eq(&glagol_local, &slovo_supported_local);
|
|
assert_source_eq(
|
|
&glagol_numeric_struct_fields,
|
|
&slovo_supported_numeric_struct_fields,
|
|
);
|
|
assert_source_eq(&glagol_numeric_widening, &slovo_supported_numeric_widening);
|
|
assert_source_eq(&glagol_option_result, &slovo_supported_option_result);
|
|
assert_source_eq(
|
|
&glagol_option_result_flow,
|
|
&slovo_supported_option_result_flow,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_option_result_match,
|
|
&slovo_supported_option_result_match,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_option_result_payload,
|
|
&slovo_supported_option_result_payload,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_owned_string_concat,
|
|
&slovo_supported_owned_string_concat,
|
|
);
|
|
assert_source_eq(&glagol_print_bool, &slovo_supported_print_bool);
|
|
assert_source_eq(
|
|
&glagol_primitive_struct_fields,
|
|
&slovo_supported_primitive_struct_fields,
|
|
);
|
|
assert_source_eq(&glagol_random, &slovo_supported_random);
|
|
assert_source_eq(&glagol_stdin_result, &slovo_supported_stdin_result);
|
|
assert_source_eq(
|
|
&glagol_string_parse_i32_result,
|
|
&slovo_supported_string_parse_i32_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_string_parse_i64_result,
|
|
&slovo_supported_string_parse_i64_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_string_parse_bool_result,
|
|
&slovo_supported_string_parse_bool_result,
|
|
);
|
|
assert_source_eq(&glagol_result_helpers, &slovo_supported_result_helpers);
|
|
assert_source_eq(
|
|
&glagol_result_f64_bool_match,
|
|
&slovo_supported_result_f64_bool_match,
|
|
);
|
|
assert_source_eq(&glagol_standard_runtime, &slovo_supported_standard_runtime);
|
|
assert_source_eq(&glagol_time_sleep, &slovo_supported_time_sleep);
|
|
assert_source_eq(&glagol_string_print, &slovo_supported_string_print);
|
|
assert_source_eq(
|
|
&glagol_string_value_flow,
|
|
&slovo_supported_string_value_flow,
|
|
);
|
|
assert_source_eq(&glagol_struct, &slovo_supported_struct);
|
|
assert_source_eq(
|
|
&glagol_struct_value_flow,
|
|
&slovo_supported_struct_value_flow,
|
|
);
|
|
assert_source_eq(&glagol_unsafe, &slovo_supported_unsafe);
|
|
assert_source_eq(&glagol_vec_i32, &slovo_supported_vec_i32);
|
|
assert_source_eq(&glagol_vec_f64, &slovo_supported_vec_f64);
|
|
assert_source_eq(&glagol_vec_bool, &slovo_supported_vec_bool);
|
|
assert_source_eq(&glagol_vec_string, &slovo_supported_vec_string);
|
|
assert_source_eq(&glagol_while, &slovo_supported_while);
|
|
assert_source_eq(
|
|
&glagol_project_enum_imports_manifest,
|
|
&slovo_project_enum_imports_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_enum_imports_readings,
|
|
&slovo_project_enum_imports_readings,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_enum_imports_main,
|
|
&slovo_project_enum_imports_main,
|
|
);
|
|
assert!(glagol_project_std_layout_local_math_manifest.is_file());
|
|
assert!(glagol_project_std_layout_local_math_math.is_file());
|
|
assert!(glagol_project_std_layout_local_math_main.is_file());
|
|
assert!(glagol_project_std_layout_local_num_manifest.is_file());
|
|
assert!(glagol_project_std_layout_local_num_num.is_file());
|
|
assert!(glagol_project_std_layout_local_num_main.is_file());
|
|
assert!(glagol_project_std_layout_local_process_manifest.is_file());
|
|
assert!(glagol_project_std_layout_local_process_process.is_file());
|
|
assert!(glagol_project_std_layout_local_process_main.is_file());
|
|
assert!(glagol_project_std_layout_local_result_manifest.is_file());
|
|
assert!(glagol_project_std_layout_local_result_result.is_file());
|
|
assert!(glagol_project_std_layout_local_result_main.is_file());
|
|
assert!(glagol_project_std_layout_local_string_manifest.is_file());
|
|
assert!(glagol_project_std_layout_local_string_string.is_file());
|
|
assert!(glagol_project_std_layout_local_string_main.is_file());
|
|
assert!(glagol_project_std_layout_local_cli_manifest.is_file());
|
|
assert!(glagol_project_std_layout_local_cli_cli.is_file());
|
|
assert!(glagol_project_std_layout_local_cli_process.is_file());
|
|
assert!(glagol_project_std_layout_local_cli_string.is_file());
|
|
assert!(glagol_project_std_layout_local_cli_main.is_file());
|
|
assert!(glagol_project_std_layout_local_vec_i32_manifest.is_file());
|
|
assert!(glagol_project_std_layout_local_vec_i32_vec_i32.is_file());
|
|
assert!(glagol_project_std_layout_local_vec_i32_main.is_file());
|
|
assert_source_eq(
|
|
&glagol_project_std_import_time_manifest,
|
|
&slovo_project_std_import_time_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_time_main,
|
|
&slovo_project_std_import_time_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_random_manifest,
|
|
&slovo_project_std_import_random_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_random_main,
|
|
&slovo_project_std_import_random_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_env_manifest,
|
|
&slovo_project_std_import_env_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_env_main,
|
|
&slovo_project_std_import_env_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_fs_manifest,
|
|
&slovo_project_std_import_fs_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_fs_main,
|
|
&slovo_project_std_import_fs_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_process_manifest,
|
|
&slovo_project_std_import_process_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_process_main,
|
|
&slovo_project_std_import_process_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_string_manifest,
|
|
&slovo_project_std_import_string_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_string_main,
|
|
&slovo_project_std_import_string_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_num_manifest,
|
|
&slovo_project_std_import_num_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_num_main,
|
|
&slovo_project_std_import_num_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_io_manifest,
|
|
&slovo_project_std_import_io_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_io_main,
|
|
&slovo_project_std_import_io_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_cli_manifest,
|
|
&slovo_project_std_import_cli_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_cli_main,
|
|
&slovo_project_std_import_cli_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_vec_i32_manifest,
|
|
&slovo_project_std_import_vec_i32_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_vec_i32_main,
|
|
&slovo_project_std_import_vec_i32_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_vec_f64_manifest,
|
|
&slovo_project_std_import_vec_f64_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_vec_f64_main,
|
|
&slovo_project_std_import_vec_f64_main,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_vec_bool_manifest,
|
|
&slovo_project_std_import_vec_bool_manifest,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_project_std_import_vec_bool_main,
|
|
&slovo_project_std_import_vec_bool_main,
|
|
);
|
|
assert_source_eq(&glagol_formatter_canonical, &slovo_formatter_canonical);
|
|
assert_source_eq(
|
|
&glagol_formatter_array_direct_scalars,
|
|
&slovo_formatter_array_direct_scalars,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_array_direct_scalars_value_flow,
|
|
&slovo_formatter_array_direct_scalars_value_flow,
|
|
);
|
|
assert_source_eq(&glagol_formatter_array_enum, &slovo_formatter_array_enum);
|
|
assert_source_eq(
|
|
&glagol_formatter_array_string,
|
|
&slovo_formatter_array_string,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_array_string_value_flow,
|
|
&slovo_formatter_array_string_value_flow,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_array_struct_elements,
|
|
&slovo_formatter_array_struct_elements,
|
|
);
|
|
assert_source_eq(&glagol_formatter_array, &slovo_formatter_array);
|
|
assert_source_eq(
|
|
&glagol_formatter_array_value_flow,
|
|
&slovo_formatter_array_value_flow,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_boolean_logic,
|
|
&slovo_formatter_boolean_logic,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_checked_i64_to_i32,
|
|
&slovo_formatter_checked_i64_to_i32,
|
|
);
|
|
assert_source_eq(&glagol_formatter_comments, &slovo_formatter_comments);
|
|
assert_source_eq(
|
|
&glagol_formatter_enum_payload_direct_scalars,
|
|
&slovo_formatter_enum_payload_direct_scalars,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_enum_payload_structs,
|
|
&slovo_formatter_enum_payload_structs,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_enum_payload_i32,
|
|
&slovo_formatter_enum_payload_i32,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_enum_struct_fields,
|
|
&slovo_formatter_enum_struct_fields,
|
|
);
|
|
assert_source_eq(&glagol_formatter_host_io, &slovo_formatter_host_io);
|
|
assert_source_eq(
|
|
&glagol_formatter_host_io_result,
|
|
&slovo_formatter_host_io_result,
|
|
);
|
|
assert_source_eq(&glagol_formatter_if, &slovo_formatter_if);
|
|
assert_source_eq(
|
|
&glagol_formatter_integer_bitwise,
|
|
&slovo_formatter_integer_bitwise,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_integer_remainder,
|
|
&slovo_formatter_integer_remainder,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_integer_to_string,
|
|
&slovo_formatter_integer_to_string,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_f64_to_string,
|
|
&slovo_formatter_f64_to_string,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_f64_to_i32_result,
|
|
&slovo_formatter_f64_to_i32_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_f64_to_i64_result,
|
|
&slovo_formatter_f64_to_i64_result,
|
|
);
|
|
assert_source_eq(&glagol_formatter_composite, &slovo_formatter_composite);
|
|
assert_source_eq(
|
|
&glagol_formatter_composite_struct_fields,
|
|
&slovo_formatter_composite_struct_fields,
|
|
);
|
|
assert_source_eq(&glagol_formatter_test, &slovo_formatter_test);
|
|
assert_source_eq(&glagol_formatter_local, &slovo_formatter_local);
|
|
assert_source_eq(
|
|
&glagol_formatter_numeric_struct_fields,
|
|
&slovo_formatter_numeric_struct_fields,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_numeric_widening,
|
|
&slovo_formatter_numeric_widening,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_option_result,
|
|
&slovo_formatter_option_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_option_result_flow,
|
|
&slovo_formatter_option_result_flow,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_option_result_match,
|
|
&slovo_formatter_option_result_match,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_option_result_payload,
|
|
&slovo_formatter_option_result_payload,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_owned_string_concat,
|
|
&slovo_formatter_owned_string_concat,
|
|
);
|
|
assert_source_eq(&glagol_formatter_print_bool, &slovo_formatter_print_bool);
|
|
assert_source_eq(
|
|
&glagol_formatter_primitive_struct_fields,
|
|
&slovo_formatter_primitive_struct_fields,
|
|
);
|
|
assert_source_eq(&glagol_formatter_random, &slovo_formatter_random);
|
|
assert_source_eq(
|
|
&glagol_formatter_stdin_result,
|
|
&slovo_formatter_stdin_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_string_parse_i32_result,
|
|
&slovo_formatter_string_parse_i32_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_string_parse_i64_result,
|
|
&slovo_formatter_string_parse_i64_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_string_parse_bool_result,
|
|
&slovo_formatter_string_parse_bool_result,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_result_helpers,
|
|
&slovo_formatter_result_helpers,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_standard_runtime,
|
|
&slovo_formatter_standard_runtime,
|
|
);
|
|
assert_source_eq(&glagol_formatter_time_sleep, &slovo_formatter_time_sleep);
|
|
assert_source_eq(
|
|
&glagol_formatter_string_print,
|
|
&slovo_formatter_string_print,
|
|
);
|
|
assert_source_eq(
|
|
&glagol_formatter_string_value_flow,
|
|
&slovo_formatter_string_value_flow,
|
|
);
|
|
assert_source_eq(&glagol_formatter_struct, &slovo_formatter_struct);
|
|
assert_source_eq(
|
|
&glagol_formatter_struct_value_flow,
|
|
&slovo_formatter_struct_value_flow,
|
|
);
|
|
assert_source_eq(&glagol_formatter_unsafe, &slovo_formatter_unsafe);
|
|
assert_source_eq(&glagol_formatter_vec_i32, &slovo_formatter_vec_i32);
|
|
assert_source_eq(&glagol_vec_f64, &slovo_formatter_vec_f64);
|
|
assert_source_eq(&glagol_vec_bool, &slovo_formatter_vec_bool);
|
|
assert_source_eq(&glagol_formatter_while, &slovo_formatter_while);
|
|
}
|
|
|
|
#[test]
|
|
#[ignore = "requires sibling slovo std/ contract files; default glagol tests stay standalone"]
|
|
fn hermeticum_slovo_std_source_layout_alpha_is_preserved() {
|
|
let repo = repo_root();
|
|
let slovo_std = repo.join("lib/std");
|
|
|
|
assert_slovo_std_source_layout_alpha(&repo, &slovo_std);
|
|
}
|
|
|
|
fn assert_supported_fixtures(repo: &Path) {
|
|
let supported_dir = repo.join("examples");
|
|
let mut files = read_dir_files(&supported_dir);
|
|
files.sort();
|
|
|
|
assert_eq!(
|
|
files,
|
|
vec![
|
|
supported_dir.join("add.slo"),
|
|
supported_dir.join("array-direct-scalars-value-flow.slo"),
|
|
supported_dir.join("array-direct-scalars.slo"),
|
|
supported_dir.join("array-enum.slo"),
|
|
supported_dir.join("array-string-value-flow.slo"),
|
|
supported_dir.join("array-string.slo"),
|
|
supported_dir.join("array-struct-elements.slo"),
|
|
supported_dir.join("array-struct-fields.slo"),
|
|
supported_dir.join("array-value-flow.slo"),
|
|
supported_dir.join("array.slo"),
|
|
supported_dir.join("boolean-logic.slo"),
|
|
supported_dir.join("checked-i64-to-i32-conversion.slo"),
|
|
supported_dir.join("composite-locals.slo"),
|
|
supported_dir.join("composite-struct-fields.slo"),
|
|
supported_dir.join("enum-basic.slo"),
|
|
supported_dir.join("enum-payload-direct-scalars.slo"),
|
|
supported_dir.join("enum-payload-i32.slo"),
|
|
supported_dir.join("enum-payload-structs.slo"),
|
|
supported_dir.join("enum-struct-fields.slo"),
|
|
supported_dir.join("f64-numeric-primitive.slo"),
|
|
supported_dir.join("f64-to-i32-result.slo"),
|
|
supported_dir.join("f64-to-i64-result.slo"),
|
|
supported_dir.join("f64-to-string.slo"),
|
|
supported_dir.join("host-io-result.slo"),
|
|
supported_dir.join("host-io.slo"),
|
|
supported_dir.join("i64-numeric-primitive.slo"),
|
|
supported_dir.join("if.slo"),
|
|
supported_dir.join("integer-bitwise.slo"),
|
|
supported_dir.join("integer-remainder.slo"),
|
|
supported_dir.join("integer-to-string.slo"),
|
|
supported_dir.join("local-variables.slo"),
|
|
supported_dir.join("numeric-struct-fields.slo"),
|
|
supported_dir.join("numeric-widening-conversions.slo"),
|
|
supported_dir.join("option-result-flow.slo"),
|
|
supported_dir.join("option-result-match.slo"),
|
|
supported_dir.join("option-result-payload.slo"),
|
|
supported_dir.join("option-result.slo"),
|
|
supported_dir.join("owned-string-concat.slo"),
|
|
supported_dir.join("primitive-struct-fields.slo"),
|
|
supported_dir.join("print-bool.slo"),
|
|
supported_dir.join("random.slo"),
|
|
supported_dir.join("result-f64-bool-match.slo"),
|
|
supported_dir.join("result-helpers.slo"),
|
|
supported_dir.join("standard-runtime.slo"),
|
|
supported_dir.join("stdin-result.slo"),
|
|
supported_dir.join("string-parse-bool-result.slo"),
|
|
supported_dir.join("string-parse-f64-result.slo"),
|
|
supported_dir.join("string-parse-i32-result.slo"),
|
|
supported_dir.join("string-parse-i64-result.slo"),
|
|
supported_dir.join("string-parse-u32-result.slo"),
|
|
supported_dir.join("string-parse-u64-result.slo"),
|
|
supported_dir.join("string-print.slo"),
|
|
supported_dir.join("string-value-flow.slo"),
|
|
supported_dir.join("struct-value-flow.slo"),
|
|
supported_dir.join("struct.slo"),
|
|
supported_dir.join("time-sleep.slo"),
|
|
supported_dir.join("u32-numeric-primitive.slo"),
|
|
supported_dir.join("u64-numeric-primitive.slo"),
|
|
supported_dir.join("unsafe.slo"),
|
|
supported_dir.join("unsigned-integer-to-string.slo"),
|
|
supported_dir.join("vec-bool.slo"),
|
|
supported_dir.join("vec-f64.slo"),
|
|
supported_dir.join("vec-i32.slo"),
|
|
supported_dir.join("vec-string.slo"),
|
|
supported_dir.join("while.slo"),
|
|
],
|
|
"promotion gate expects Glagol supported fixtures to match the current supported surface"
|
|
);
|
|
}
|
|
|
|
fn assert_slovo_supported_fixtures(repo: &Path) {
|
|
let supported_dir = repo.join("docs/language/examples/supported");
|
|
let mut files = read_dir_files(&supported_dir);
|
|
files.sort();
|
|
|
|
assert_eq!(
|
|
files,
|
|
vec![
|
|
supported_dir.join("add.slo"),
|
|
supported_dir.join("array-direct-scalars-value-flow.slo"),
|
|
supported_dir.join("array-direct-scalars.slo"),
|
|
supported_dir.join("array-enum.slo"),
|
|
supported_dir.join("array-string-value-flow.slo"),
|
|
supported_dir.join("array-string.slo"),
|
|
supported_dir.join("array-struct-elements.slo"),
|
|
supported_dir.join("array-struct-fields.slo"),
|
|
supported_dir.join("array-value-flow.slo"),
|
|
supported_dir.join("array.slo"),
|
|
supported_dir.join("boolean-logic.slo"),
|
|
supported_dir.join("checked-i64-to-i32-conversion.slo"),
|
|
supported_dir.join("composite-locals.slo"),
|
|
supported_dir.join("composite-struct-fields.slo"),
|
|
supported_dir.join("enum-basic.slo"),
|
|
supported_dir.join("enum-payload-direct-scalars.slo"),
|
|
supported_dir.join("enum-payload-i32.slo"),
|
|
supported_dir.join("enum-payload-structs.slo"),
|
|
supported_dir.join("enum-struct-fields.slo"),
|
|
supported_dir.join("f64-numeric-primitive.slo"),
|
|
supported_dir.join("f64-to-i32-result.slo"),
|
|
supported_dir.join("f64-to-i64-result.slo"),
|
|
supported_dir.join("f64-to-string.slo"),
|
|
supported_dir.join("host-io-result.slo"),
|
|
supported_dir.join("host-io.slo"),
|
|
supported_dir.join("i64-numeric-primitive.slo"),
|
|
supported_dir.join("if.slo"),
|
|
supported_dir.join("integer-bitwise.slo"),
|
|
supported_dir.join("integer-remainder.slo"),
|
|
supported_dir.join("integer-to-string.slo"),
|
|
supported_dir.join("local-variables.slo"),
|
|
supported_dir.join("numeric-struct-fields.slo"),
|
|
supported_dir.join("numeric-widening-conversions.slo"),
|
|
supported_dir.join("option-result-flow.slo"),
|
|
supported_dir.join("option-result-match.slo"),
|
|
supported_dir.join("option-result-payload.slo"),
|
|
supported_dir.join("option-result.slo"),
|
|
supported_dir.join("owned-string-concat.slo"),
|
|
supported_dir.join("primitive-struct-fields.slo"),
|
|
supported_dir.join("print-bool.slo"),
|
|
supported_dir.join("random.slo"),
|
|
supported_dir.join("result-f64-bool-match.slo"),
|
|
supported_dir.join("result-helpers.slo"),
|
|
supported_dir.join("standard-runtime.slo"),
|
|
supported_dir.join("stdin-result.slo"),
|
|
supported_dir.join("string-parse-bool-result.slo"),
|
|
supported_dir.join("string-parse-f64-result.slo"),
|
|
supported_dir.join("string-parse-i32-result.slo"),
|
|
supported_dir.join("string-parse-i64-result.slo"),
|
|
supported_dir.join("string-parse-u32-result.slo"),
|
|
supported_dir.join("string-parse-u64-result.slo"),
|
|
supported_dir.join("string-print.slo"),
|
|
supported_dir.join("string-value-flow.slo"),
|
|
supported_dir.join("struct-value-flow.slo"),
|
|
supported_dir.join("struct.slo"),
|
|
supported_dir.join("time-sleep.slo"),
|
|
supported_dir.join("top-level-test.slo"),
|
|
supported_dir.join("u32-numeric-primitive.slo"),
|
|
supported_dir.join("u64-numeric-primitive.slo"),
|
|
supported_dir.join("unsafe.slo"),
|
|
supported_dir.join("unsigned-integer-to-string.slo"),
|
|
supported_dir.join("vec-bool.slo"),
|
|
supported_dir.join("vec-f64.slo"),
|
|
supported_dir.join("vec-i32.slo"),
|
|
supported_dir.join("vec-i64.slo"),
|
|
supported_dir.join("vec-string.slo"),
|
|
supported_dir.join("while.slo"),
|
|
],
|
|
"promotion gate expects Slovo supported fixtures to match the current supported surface"
|
|
);
|
|
}
|
|
|
|
fn assert_glagol_test_fixtures(repo: &Path) {
|
|
let tests_dir = repo.join("tests");
|
|
assert_file_name_inventory(
|
|
&tests_dir,
|
|
&["slo", "fmt"],
|
|
GLAGOL_TEST_FIXTURES,
|
|
"promotion gate expects Glagol test/formatter fixtures to be explicitly inventoried",
|
|
);
|
|
}
|
|
|
|
fn assert_lowering_inspector_fixture_inventory(repo: &Path) {
|
|
assert_file_name_inventory(
|
|
&repo.join("tests"),
|
|
&["lower"],
|
|
LOWERING_INSPECTOR_FIXTURES,
|
|
"promotion gate expects lowering inspector fixtures to be explicitly inventoried",
|
|
);
|
|
}
|
|
|
|
fn assert_slovo_formatter_fixtures(repo: &Path) {
|
|
let formatter_dir = repo.join("docs/language/examples/formatter");
|
|
assert_file_name_inventory(
|
|
&formatter_dir,
|
|
&["slo"],
|
|
SLOVO_FORMATTER_FIXTURES,
|
|
"promotion gate expects Slovo formatter fixtures to be explicitly inventoried",
|
|
);
|
|
}
|
|
|
|
fn assert_slovo_v0_compatibility_fixtures(repo: &Path) {
|
|
assert_file_name_inventory(
|
|
&repo.join("docs/language/examples/compat/v0/supported"),
|
|
&["slo"],
|
|
SLOVO_V0_SUPPORTED_COMPATIBILITY_FIXTURES,
|
|
"promotion gate expects frozen Slovo v0 supported compatibility fixtures",
|
|
);
|
|
assert_file_name_inventory(
|
|
&repo.join("docs/language/examples/compat/v0/formatter"),
|
|
&["slo"],
|
|
SLOVO_V0_FORMATTER_COMPATIBILITY_FIXTURES,
|
|
"promotion gate expects frozen Slovo v0 formatter compatibility fixtures",
|
|
);
|
|
}
|
|
|
|
fn assert_slovo_std_source_layout_alpha(repo: &Path, std_dir: &Path) {
|
|
assert!(
|
|
std_dir.is_dir(),
|
|
"`{}` must exist for exp-30 std source layout alpha",
|
|
std_dir.display()
|
|
);
|
|
|
|
let mut files = read_dir_files(std_dir);
|
|
files.sort();
|
|
assert_eq!(
|
|
files,
|
|
vec![
|
|
std_dir.join("README.md"),
|
|
std_dir.join("cli.slo"),
|
|
std_dir.join("env.slo"),
|
|
std_dir.join("fs.slo"),
|
|
std_dir.join("io.slo"),
|
|
std_dir.join("json.slo"),
|
|
std_dir.join("math.slo"),
|
|
std_dir.join("net.slo"),
|
|
std_dir.join("num.slo"),
|
|
std_dir.join("option.slo"),
|
|
std_dir.join("process.slo"),
|
|
std_dir.join("random.slo"),
|
|
std_dir.join("result.slo"),
|
|
std_dir.join("string.slo"),
|
|
std_dir.join("time.slo"),
|
|
std_dir.join("vec_bool.slo"),
|
|
std_dir.join("vec_f64.slo"),
|
|
std_dir.join("vec_i32.slo"),
|
|
std_dir.join("vec_i64.slo"),
|
|
std_dir.join("vec_string.slo"),
|
|
],
|
|
"std source layout alpha expects an exact file inventory"
|
|
);
|
|
|
|
let readme = read(&std_dir.join("README.md"));
|
|
assert!(
|
|
readme.contains("source layout") || readme.contains("Source Layout"),
|
|
"std/README.md should describe std as a source-layout contract artifact"
|
|
);
|
|
|
|
for file in [
|
|
"io.slo",
|
|
"cli.slo",
|
|
"env.slo",
|
|
"fs.slo",
|
|
"math.slo",
|
|
"net.slo",
|
|
"json.slo",
|
|
"num.slo",
|
|
"option.slo",
|
|
"process.slo",
|
|
"random.slo",
|
|
"result.slo",
|
|
"string.slo",
|
|
"time.slo",
|
|
"vec_i32.slo",
|
|
] {
|
|
let path = std_dir.join(file);
|
|
assert_source_shaped_file(&path);
|
|
|
|
// Import-bearing std sources are validated through their project fixtures.
|
|
if file != "cli.slo"
|
|
&& file != "env.slo"
|
|
&& file != "fs.slo"
|
|
&& file != "io.slo"
|
|
&& file != "json.slo"
|
|
&& file != "process.slo"
|
|
&& file != "string.slo"
|
|
&& file != "vec_i32.slo"
|
|
{
|
|
let check = run_glagol([OsStr::new("check"), path.as_os_str()]);
|
|
assert_success_stdout(check, "", &format!("std source check for `{}`", file));
|
|
}
|
|
|
|
if file != "vec_i32.slo" {
|
|
let format = run_glagol([OsStr::new("--format"), path.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&read(&path),
|
|
&format!("std source formatter stability for `{}`", file),
|
|
);
|
|
}
|
|
}
|
|
|
|
let local_math = repo.join("examples/projects/std-layout-local-math/src/math.slo");
|
|
let slovo_math = read(&std_dir.join("math.slo"));
|
|
let glagol_math = read(&local_math);
|
|
assert!(
|
|
slovo_math.contains("(module math") && glagol_math.contains("(module math"),
|
|
"both Slovo std/math.slo and the Glagol local fixture should use explicit `math` module source shape"
|
|
);
|
|
assert!(
|
|
!slovo_math.contains("std.") && !glagol_math.contains("std."),
|
|
"exp-39 standard math helpers must stay source-authored without compiler-known std runtime calls"
|
|
);
|
|
assert_eq!(
|
|
normalize_local_math_fixture_helpers(&glagol_math),
|
|
slovo_math.trim_end(),
|
|
"Glagol local math helper source must match sibling Slovo std/math.slo"
|
|
);
|
|
for helper in STANDARD_MATH_SOURCE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_math.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/math.slo is missing exp-39 helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_math.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local math fixture is missing exp-39 helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_option = repo.join("examples/projects/std-layout-local-option/src/option.slo");
|
|
let slovo_option = read(&std_dir.join("option.slo"));
|
|
let glagol_option = read(&local_option);
|
|
assert!(
|
|
slovo_option.contains("(module option") && glagol_option.contains("(module option"),
|
|
"both Slovo std/option.slo and the Glagol local fixture should use explicit `option` module source shape"
|
|
);
|
|
assert!(
|
|
!slovo_option.contains("std.") && !glagol_option.contains("std."),
|
|
"exp-36 standard option helpers must stay source-authored without compiler-known std runtime calls"
|
|
);
|
|
for helper in STANDARD_OPTION_SOURCE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_option.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/option.slo is missing exp-36 helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_option.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local option fixture is missing exp-36 helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_OPTION_RESULT_BRIDGE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_option.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/option.slo is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_option.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local option fixture is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_result = repo.join("examples/projects/std-layout-local-result/src/result.slo");
|
|
let slovo_result = read(&std_dir.join("result.slo"));
|
|
let glagol_result = read(&local_result);
|
|
assert!(
|
|
slovo_result.contains("(module result") && glagol_result.contains("(module result"),
|
|
"both Slovo std/result.slo and the Glagol local fixture should use explicit `result` module source shape"
|
|
);
|
|
assert!(
|
|
!slovo_result.contains("std.result.map")
|
|
&& !slovo_result.contains("std.result.and_then")
|
|
&& !slovo_result.contains("std.result.unwrap_or")
|
|
&& !glagol_result.contains("std.result.map")
|
|
&& !glagol_result.contains("std.result.and_then")
|
|
&& !glagol_result.contains("std.result.unwrap_or"),
|
|
"exp-33 standard result source helpers must not introduce deferred compiler-known result helpers"
|
|
);
|
|
for helper in STANDARD_RESULT_SOURCE_SEARCH_ALPHA {
|
|
assert!(
|
|
slovo_result.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/result.slo is missing exp-33 helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_result.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local result fixture is missing exp-33 helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_RESULT_OPTION_BRIDGE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_result.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/result.slo is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_result.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local result fixture is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let slovo_string = read(&std_dir.join("string.slo"));
|
|
assert!(
|
|
slovo_string.starts_with("(module string (export "),
|
|
"Slovo std/string.slo must directly export imported helpers"
|
|
);
|
|
assert!(
|
|
slovo_string.contains("(fn parse_bool_result ")
|
|
&& slovo_string.contains("(std.string.parse_bool_result value)")
|
|
&& slovo_string.contains(
|
|
"(import std.result (ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
),
|
|
"Slovo std/string.slo must preserve parse result helpers and the std.result option bridge import"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_string,
|
|
&[
|
|
"std.result",
|
|
"std.string.parse_bool_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i32_result",
|
|
"std.string.byte_at_result",
|
|
"std.string.slice_result",
|
|
"std.string.starts_with",
|
|
"std.string.ends_with",
|
|
"std.string.concat",
|
|
"std.string.len",
|
|
],
|
|
"Slovo std/string.slo must not introduce other compiler-known std names",
|
|
);
|
|
for helper in STANDARD_STRING_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_string.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/string.slo is missing exp-48 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_num = repo.join("examples/projects/std-layout-local-num/src/num.slo");
|
|
let slovo_num = read(&std_dir.join("num.slo"));
|
|
let glagol_num = read(&local_num);
|
|
assert!(
|
|
slovo_num.starts_with("(module num (export ")
|
|
&& glagol_num.starts_with("(module num (export "),
|
|
"both Slovo std/num.slo and the Glagol local fixture must directly export imported helpers"
|
|
);
|
|
for source in [&slovo_num, &glagol_num] {
|
|
assert_std_only_contains(
|
|
source,
|
|
&[
|
|
"std.num.i32_to_i64",
|
|
"std.num.i32_to_f64",
|
|
"std.num.i64_to_f64",
|
|
"std.num.i64_to_i32_result",
|
|
"std.num.f64_to_i32_result",
|
|
"std.num.f64_to_i64_result",
|
|
"std.num.i32_to_string",
|
|
"std.num.u32_to_string",
|
|
"std.num.i64_to_string",
|
|
"std.num.u64_to_string",
|
|
"std.num.f64_to_string",
|
|
],
|
|
"exp-64 standard num facade must not introduce other compiler-known std names",
|
|
);
|
|
assert!(
|
|
!source.contains("saturat")
|
|
&& !source.contains("round")
|
|
&& !source.contains("floor")
|
|
&& !source.contains("ceil")
|
|
&& !source.contains("generic"),
|
|
"exp-64 standard num facade must not claim deferred numeric conversion policies or generic abstractions"
|
|
);
|
|
}
|
|
for helper in STANDARD_NUM_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_num.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/num.slo is missing exp-64 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_num.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local num fixture is missing exp-64 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let slovo_io = read(&std_dir.join("io.slo"));
|
|
assert!(
|
|
slovo_io.starts_with("(module io (export "),
|
|
"Slovo std/io.slo must directly export imported helpers"
|
|
);
|
|
assert!(
|
|
slovo_io.contains(
|
|
"(import std.result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
) && slovo_io.contains(
|
|
"(import std.string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))",
|
|
) && slovo_io.contains("(std.io.read_stdin_result)"),
|
|
"Slovo std/io.slo must preserve stdin-result source helpers over std.result and std.string bridge imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_io,
|
|
&[
|
|
"std.io.print_i32",
|
|
"std.io.print_i64",
|
|
"std.io.print_u32",
|
|
"std.io.print_u64",
|
|
"std.io.print_f64",
|
|
"std.io.print_string",
|
|
"std.io.print_bool",
|
|
"std.io.read_stdin_result",
|
|
"std.result",
|
|
"std.string",
|
|
],
|
|
"Slovo std/io.slo must not introduce other compiler-known std names",
|
|
);
|
|
for helper in STANDARD_IO_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_io.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/io.slo is missing exp-49 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_vec_i32 = repo.join("examples/projects/std-layout-local-vec_i32/src/vec_i32.slo");
|
|
let local_vec_i32_option =
|
|
repo.join("examples/projects/std-layout-local-vec_i32/src/option.slo");
|
|
let slovo_vec_i32 = read(&std_dir.join("vec_i32.slo"));
|
|
let glagol_vec_i32 = read(&local_vec_i32);
|
|
let glagol_vec_i32_option = read(&local_vec_i32_option);
|
|
assert!(
|
|
slovo_vec_i32.starts_with("(module vec_i32 (export ")
|
|
&& glagol_vec_i32.starts_with("(module vec_i32 (export "),
|
|
"both Slovo std/vec_i32.slo and the Glagol local fixture must directly export imported helpers"
|
|
);
|
|
assert!(
|
|
glagol_vec_i32_option.starts_with("(module option (export "),
|
|
"Glagol local vec_i32 option helper source must stay an explicit local module"
|
|
);
|
|
assert_eq!(
|
|
normalize_local_vec_i32_fixture_helpers(&glagol_vec_i32),
|
|
slovo_vec_i32.trim_end(),
|
|
"Glagol local vec_i32 helper source must match sibling Slovo std/vec_i32.slo"
|
|
);
|
|
for source in [&slovo_vec_i32, &glagol_vec_i32] {
|
|
assert_std_only_contains(
|
|
source,
|
|
&[
|
|
"std.vec.i32.empty",
|
|
"std.vec.i32.append",
|
|
"std.vec.i32.len",
|
|
"std.vec.i32.index",
|
|
"std.option",
|
|
],
|
|
"exp-93 standard vec_i32 facade must not introduce other compiler-known std names",
|
|
);
|
|
assert!(
|
|
!source.contains("capacity")
|
|
&& !source.contains("reserve")
|
|
&& !source.contains("shrink")
|
|
&& !source.contains("sort")
|
|
&& !source.contains("map")
|
|
&& !source.contains("filter")
|
|
&& !source.contains("(vec i64)")
|
|
&& !source.contains("(vec f64)")
|
|
&& !source.contains("(vec string)")
|
|
&& !source.contains("(vec bool)")
|
|
&& !source.contains("(option i64)")
|
|
&& !source.contains("(option f64)")
|
|
&& !source.contains("(option string)")
|
|
&& !source.contains("(option bool)"),
|
|
"exp-93 standard vec_i32 facade must stay limited to concrete i32 vec and option helpers"
|
|
);
|
|
}
|
|
for helper in STANDARD_VEC_I32_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_vec_i32.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/vec_i32.slo is missing exp-93 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_vec_i32.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local vec_i32 fixture is missing exp-93 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_process = repo.join("examples/projects/std-layout-local-process/src/process.slo");
|
|
let local_process_string =
|
|
repo.join("examples/projects/std-layout-local-process/src/string.slo");
|
|
let slovo_process = read(&std_dir.join("process.slo"));
|
|
let glagol_process = read(&local_process);
|
|
let glagol_process_string = read(&local_process_string);
|
|
assert!(
|
|
slovo_process.starts_with("(module process (export ")
|
|
&& glagol_process.starts_with("(module process (export "),
|
|
"both Slovo std/process.slo and the Glagol local fixture must directly export imported helpers"
|
|
);
|
|
assert!(
|
|
slovo_process.contains("(std.process.argc)")
|
|
&& slovo_process.contains("(std.process.arg index)")
|
|
&& slovo_process.contains("(std.process.arg_result index)")
|
|
&& slovo_process.contains(
|
|
"(import std.result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& slovo_process.contains("(std.string.parse_i32_result text)")
|
|
&& slovo_process.contains("(std.string.parse_u32_result text)")
|
|
&& slovo_process.contains("(std.string.parse_i64_result text)")
|
|
&& slovo_process.contains("(std.string.parse_u64_result text)")
|
|
&& slovo_process.contains("(std.string.parse_f64_result text)")
|
|
&& slovo_process.contains("(std.string.parse_bool_result text)")
|
|
&& glagol_process.contains(
|
|
"(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& glagol_process.contains("(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))")
|
|
&& glagol_process.contains("(std.process.argc)")
|
|
&& glagol_process.contains("(std.process.arg index)")
|
|
&& glagol_process.contains("(std.process.arg_result index)")
|
|
&& glagol_process_string.starts_with("(module string (export ")
|
|
&& glagol_process_string.contains(
|
|
"(import result (ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
),
|
|
"exp-67 standard process facade must stay backed by existing promoted process and parse result calls"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_process,
|
|
&[
|
|
"std.process.arg_result",
|
|
"std.process.argc",
|
|
"std.process.arg",
|
|
"std.result",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Slovo std/process.slo must not introduce other compiler-known std names",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_process,
|
|
&[
|
|
"std.process.arg_result",
|
|
"std.process.argc",
|
|
"std.process.arg",
|
|
],
|
|
"Glagol local process fixture must not introduce direct compiler-known std names beyond process calls",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_process_string,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Glagol local process string fixture must not introduce other compiler-known std names",
|
|
);
|
|
assert!(
|
|
!slovo_process.contains("spawn")
|
|
&& !slovo_process.contains("exit")
|
|
&& !slovo_process.contains("cwd")
|
|
&& !slovo_process.contains("signal")
|
|
&& !glagol_process.contains("spawn")
|
|
&& !glagol_process.contains("exit")
|
|
&& !glagol_process.contains("cwd")
|
|
&& !glagol_process.contains("signal"),
|
|
"exp-67 standard process facade must not claim deferred process APIs"
|
|
);
|
|
for helper in STANDARD_PROCESS_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_process.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/process.slo is missing exp-67 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_process.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local process fixture is missing exp-67 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_cli = repo.join("examples/projects/std-layout-local-cli/src/cli.slo");
|
|
let local_cli_process = repo.join("examples/projects/std-layout-local-cli/src/process.slo");
|
|
let local_cli_string = repo.join("examples/projects/std-layout-local-cli/src/string.slo");
|
|
let slovo_cli = read(&std_dir.join("cli.slo"));
|
|
let glagol_cli = read(&local_cli);
|
|
let glagol_cli_process = read(&local_cli_process);
|
|
let glagol_cli_string = read(&local_cli_string);
|
|
assert!(
|
|
slovo_cli.starts_with("(module cli (export "),
|
|
"Slovo std/cli.slo must directly export imported helpers"
|
|
);
|
|
assert!(
|
|
slovo_cli.contains("(import std.process (arg_result))")
|
|
&& slovo_cli.contains(
|
|
"(import std.result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& slovo_cli
|
|
.contains("(import std.string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))"),
|
|
"standard cli facade must use transitive standard-source imports, including the std.result option bridge"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_cli,
|
|
&["std.process", "std.result", "std.string"],
|
|
"Slovo std/cli.slo must not use compiler-known std runtime names directly",
|
|
);
|
|
assert!(
|
|
glagol_cli.starts_with("(module cli (export "),
|
|
"Glagol local cli fixture must stay an explicit local module export"
|
|
);
|
|
assert!(
|
|
glagol_cli.contains("(import process (arg_result))")
|
|
&& glagol_cli.contains(
|
|
"(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))"
|
|
)
|
|
&& glagol_cli.contains(
|
|
"(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))"
|
|
)
|
|
&& !glagol_cli.contains("std."),
|
|
"Glagol local cli fixture must stay a source-authored local import chain"
|
|
);
|
|
assert!(
|
|
glagol_cli_process.starts_with("(module process (export ")
|
|
&& glagol_cli_process.contains(
|
|
"(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& glagol_cli_process.contains("(std.process.argc)")
|
|
&& glagol_cli_process.contains("(std.process.arg index)")
|
|
&& glagol_cli_process.contains("(std.process.arg_result index)")
|
|
&& glagol_cli_process.contains("(std.string.parse_i32_result text)")
|
|
&& glagol_cli_process.contains("(std.string.parse_u32_result text)")
|
|
&& glagol_cli_process.contains("(std.string.parse_i64_result text)")
|
|
&& glagol_cli_process.contains("(std.string.parse_u64_result text)")
|
|
&& glagol_cli_process.contains("(std.string.parse_f64_result text)")
|
|
&& glagol_cli_process.contains("(std.string.parse_bool_result text)"),
|
|
"Glagol local cli process fixture must stay aligned with the local process facade surface"
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_cli_process,
|
|
&[
|
|
"std.process.arg_result",
|
|
"std.process.argc",
|
|
"std.process.arg",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Glagol local cli process fixture must not introduce other compiler-known std names",
|
|
);
|
|
assert!(
|
|
glagol_cli_string.starts_with("(module string (export ")
|
|
&& glagol_cli_string.contains(
|
|
"(import result (ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
),
|
|
"Glagol local cli string fixture must stay a local parse-result helper module"
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_cli_string,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Glagol local cli string fixture must not introduce other compiler-known std names",
|
|
);
|
|
for helper in STANDARD_CLI_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_cli.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/cli.slo is missing CLI facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_cli.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local cli fixture is missing exp-78 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_STRING_PARSE_RESULT_HELPERS_ALPHA {
|
|
assert!(
|
|
glagol_cli_string.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local cli string fixture is missing parse helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_time = repo.join("examples/projects/std-layout-local-time/src/time.slo");
|
|
let slovo_time = read(&std_dir.join("time.slo"));
|
|
let glagol_time = read(&local_time);
|
|
assert!(
|
|
slovo_time.contains("(module time") && glagol_time.contains("(module time"),
|
|
"both Slovo std/time.slo and the Glagol local fixture should use explicit `time` module source shape"
|
|
);
|
|
assert!(
|
|
slovo_time.contains("(std.time.monotonic_ms)")
|
|
&& slovo_time.contains("(std.time.sleep_ms 0)")
|
|
&& glagol_time.contains("(std.time.monotonic_ms)")
|
|
&& glagol_time.contains("(std.time.sleep_ms 0)"),
|
|
"exp-37 standard time facade must stay backed by the existing promoted std.time calls"
|
|
);
|
|
for helper in STANDARD_TIME_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_time.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/time.slo is missing exp-37 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_time.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local time fixture is missing exp-37 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
assert!(
|
|
!slovo_time.contains("std.time.now")
|
|
&& !glagol_time.contains("std.time.now")
|
|
&& !slovo_time.contains("calendar")
|
|
&& !glagol_time.contains("calendar")
|
|
&& !slovo_time.contains("timezone")
|
|
&& !glagol_time.contains("timezone")
|
|
&& !slovo_time.contains("async")
|
|
&& !glagol_time.contains("async")
|
|
&& !slovo_time.contains("cancel")
|
|
&& !glagol_time.contains("cancel")
|
|
&& !slovo_time.contains("schedule")
|
|
&& !glagol_time.contains("schedule"),
|
|
"exp-37 standard time facade must not claim deferred time APIs or scheduling semantics"
|
|
);
|
|
|
|
let local_random = repo.join("examples/projects/std-layout-local-random/src/random.slo");
|
|
let slovo_random = read(&std_dir.join("random.slo"));
|
|
let glagol_random = read(&local_random);
|
|
assert!(
|
|
slovo_random.contains("(module random") && glagol_random.contains("(module random"),
|
|
"both Slovo std/random.slo and the Glagol local fixture should use explicit `random` module source shape"
|
|
);
|
|
assert!(
|
|
slovo_random.contains("(std.random.i32)") && glagol_random.contains("(std.random.i32)"),
|
|
"exp-38 standard random facade must stay backed by the existing promoted std.random.i32 call"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_random,
|
|
&["std.random.i32"],
|
|
"Slovo std/random.slo must not introduce other compiler-known std names",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_random,
|
|
&["std.random.i32"],
|
|
"Glagol local random fixture must not introduce other compiler-known std names",
|
|
);
|
|
assert!(
|
|
!slovo_random.contains("seed")
|
|
&& !glagol_random.contains("seed")
|
|
&& !slovo_random.contains("range")
|
|
&& !glagol_random.contains("range")
|
|
&& !slovo_random.contains("bytes")
|
|
&& !glagol_random.contains("bytes")
|
|
&& !slovo_random.contains("float")
|
|
&& !glagol_random.contains("float")
|
|
&& !slovo_random.contains("uuid")
|
|
&& !glagol_random.contains("uuid")
|
|
&& !slovo_random.contains("crypto")
|
|
&& !glagol_random.contains("crypto"),
|
|
"exp-38 standard random facade must not claim deferred random APIs"
|
|
);
|
|
for helper in STANDARD_RANDOM_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_random.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/random.slo is missing exp-38 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_random.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local random fixture is missing exp-38 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_env = repo.join("examples/projects/std-layout-local-env/src/env.slo");
|
|
let local_env_string = repo.join("examples/projects/std-layout-local-env/src/string.slo");
|
|
let slovo_env = read(&std_dir.join("env.slo"));
|
|
let glagol_env = read(&local_env);
|
|
let glagol_env_string = read(&local_env_string);
|
|
assert!(
|
|
slovo_env.contains("(module env") && glagol_env.contains("(module env"),
|
|
"both Slovo std/env.slo and the Glagol local fixture should use explicit `env` module source shape"
|
|
);
|
|
assert!(
|
|
slovo_env.contains("(std.env.get name)")
|
|
&& slovo_env.contains("(std.env.get_result name)")
|
|
&& slovo_env.contains(
|
|
"(import std.result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& slovo_env.contains("(std.string.parse_i32_result text)")
|
|
&& slovo_env.contains("(std.string.parse_u32_result text)")
|
|
&& slovo_env.contains("(std.string.parse_i64_result text)")
|
|
&& slovo_env.contains("(std.string.parse_u64_result text)")
|
|
&& slovo_env.contains("(std.string.parse_f64_result text)")
|
|
&& slovo_env.contains("(std.string.parse_bool_result text)")
|
|
&& glagol_env.contains(
|
|
"(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& glagol_env.contains("(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))")
|
|
&& glagol_env.contains("(std.env.get name)")
|
|
&& glagol_env.contains("(std.env.get_result name)")
|
|
&& glagol_env_string.starts_with("(module string (export ")
|
|
&& glagol_env_string.contains(
|
|
"(import result (ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
),
|
|
"exp-65 standard env facade must stay backed by the existing promoted env and parse result calls"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_env,
|
|
&[
|
|
"std.env.get_result",
|
|
"std.env.get",
|
|
"std.result",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Slovo std/env.slo must not introduce other compiler-known std names",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_env,
|
|
&["std.env.get_result", "std.env.get"],
|
|
"Glagol local env fixture must not introduce direct compiler-known std names beyond env lookup",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_env_string,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Glagol local env string fixture must not introduce other compiler-known std names",
|
|
);
|
|
assert!(
|
|
!slovo_env.contains("set")
|
|
&& !glagol_env.contains("set")
|
|
&& !slovo_env.contains("unset")
|
|
&& !glagol_env.contains("unset")
|
|
&& !slovo_env.contains("enumer")
|
|
&& !glagol_env.contains("enumer")
|
|
&& !slovo_env.contains("platform")
|
|
&& !glagol_env.contains("platform")
|
|
&& !slovo_env.contains("host_error")
|
|
&& !glagol_env.contains("host_error")
|
|
&& !slovo_env.contains("errno")
|
|
&& !glagol_env.contains("errno"),
|
|
"exp-65 standard env facade must not claim deferred env APIs or rich host errors"
|
|
);
|
|
for helper in STANDARD_ENV_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_env.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/env.slo is missing exp-65 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_env.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local env fixture is missing exp-65 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_fs = repo.join("examples/projects/std-layout-local-fs/src/fs.slo");
|
|
let local_fs_string = repo.join("examples/projects/std-layout-local-fs/src/string.slo");
|
|
let slovo_fs = read(&std_dir.join("fs.slo"));
|
|
let glagol_fs = read(&local_fs);
|
|
let glagol_fs_string = read(&local_fs_string);
|
|
assert!(
|
|
slovo_fs.contains("(module fs") && glagol_fs.contains("(module fs"),
|
|
"both Slovo std/fs.slo and the Glagol local fixture should use explicit `fs` module source shape"
|
|
);
|
|
assert!(
|
|
slovo_fs.contains("(std.fs.read_text path)")
|
|
&& slovo_fs.contains("(std.fs.read_text_result path)")
|
|
&& slovo_fs.contains("(std.fs.write_text path text)")
|
|
&& slovo_fs.contains("(std.fs.write_text_result path text)")
|
|
&& slovo_fs.contains("(std.fs.exists path)")
|
|
&& slovo_fs.contains("(std.fs.is_file path)")
|
|
&& slovo_fs.contains("(std.fs.is_dir path)")
|
|
&& slovo_fs.contains("(std.fs.remove_file_result path)")
|
|
&& slovo_fs.contains("(std.fs.create_dir_result path)")
|
|
&& slovo_fs.contains("(std.fs.open_text_read_result path)")
|
|
&& slovo_fs.contains("(std.fs.read_open_text_result handle)")
|
|
&& slovo_fs.contains("(std.fs.close_result handle)")
|
|
&& slovo_fs.contains(
|
|
"(import std.result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& slovo_fs.contains("(std.string.parse_i32_result text)")
|
|
&& slovo_fs.contains("(std.string.parse_u32_result text)")
|
|
&& slovo_fs.contains("(std.string.parse_i64_result text)")
|
|
&& slovo_fs.contains("(std.string.parse_u64_result text)")
|
|
&& slovo_fs.contains("(std.string.parse_f64_result text)")
|
|
&& slovo_fs.contains("(std.string.parse_bool_result text)")
|
|
&& glagol_fs.contains(
|
|
"(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& glagol_fs.contains("(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))")
|
|
&& glagol_fs.contains("(std.fs.read_text path)")
|
|
&& glagol_fs.contains("(std.fs.read_text_result path)")
|
|
&& glagol_fs.contains("(std.fs.write_text path text)")
|
|
&& glagol_fs.contains("(std.fs.write_text_result path text)")
|
|
&& glagol_fs.contains("(std.fs.exists path)")
|
|
&& glagol_fs.contains("(std.fs.is_file path)")
|
|
&& glagol_fs.contains("(std.fs.is_dir path)")
|
|
&& glagol_fs.contains("(std.fs.remove_file_result path)")
|
|
&& glagol_fs.contains("(std.fs.create_dir_result path)")
|
|
&& glagol_fs.contains("(std.fs.open_text_read_result path)")
|
|
&& glagol_fs.contains("(std.fs.read_open_text_result handle)")
|
|
&& glagol_fs.contains("(std.fs.close_result handle)")
|
|
&& glagol_fs_string.starts_with("(module string (export ")
|
|
&& glagol_fs_string.contains(
|
|
"(import result (ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
),
|
|
"exp-66 standard fs facade must stay backed by the existing promoted fs and parse result calls"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_fs,
|
|
&[
|
|
"std.fs.read_text_result",
|
|
"std.fs.write_text_result",
|
|
"std.fs.read_text",
|
|
"std.fs.write_text",
|
|
"std.fs.exists",
|
|
"std.fs.is_file",
|
|
"std.fs.is_dir",
|
|
"std.fs.remove_file_result",
|
|
"std.fs.create_dir_result",
|
|
"std.fs.open_text_read_result",
|
|
"std.fs.read_open_text_result",
|
|
"std.fs.close_result",
|
|
"std.result",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Slovo std/fs.slo must not introduce other compiler-known std names",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_fs,
|
|
&[
|
|
"std.fs.read_text_result",
|
|
"std.fs.write_text_result",
|
|
"std.fs.read_text",
|
|
"std.fs.write_text",
|
|
"std.fs.exists",
|
|
"std.fs.is_file",
|
|
"std.fs.is_dir",
|
|
"std.fs.remove_file_result",
|
|
"std.fs.create_dir_result",
|
|
"std.fs.open_text_read_result",
|
|
"std.fs.read_open_text_result",
|
|
"std.fs.close_result",
|
|
],
|
|
"Glagol local fs fixture must not introduce direct compiler-known std names beyond fs text calls",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_fs_string,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"Glagol local fs string fixture must not introduce other compiler-known std names",
|
|
);
|
|
for source in [&slovo_fs, &glagol_fs, &glagol_fs_string] {
|
|
assert!(
|
|
!source.contains("binary")
|
|
&& !source.contains("list_dir")
|
|
&& !source.contains("walk")
|
|
&& !source.contains("stream")
|
|
&& !source.contains("async")
|
|
&& !source.contains("host_error"),
|
|
"exp-66 standard fs facade must not claim deferred fs APIs or rich host errors"
|
|
);
|
|
}
|
|
for helper in STANDARD_FS_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_fs.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/fs.slo is missing exp-66 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_fs.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local fs fixture is missing exp-66 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_net = repo.join("examples/projects/std-layout-local-net/src/net.slo");
|
|
let slovo_net = read(&std_dir.join("net.slo"));
|
|
let glagol_net = read(&local_net);
|
|
assert!(
|
|
slovo_net.contains("(module net") && glagol_net.contains("(module net"),
|
|
"both Slovo std/net.slo and the Glagol local fixture should use explicit `net` module source shape"
|
|
);
|
|
for runtime_name in STANDARD_NET_RUNTIME_NAMES {
|
|
assert!(
|
|
slovo_net.contains(runtime_name) && glagol_net.contains(runtime_name),
|
|
"standard net facade must stay backed by `{}`",
|
|
runtime_name
|
|
);
|
|
}
|
|
assert_std_only_contains(
|
|
&slovo_net,
|
|
STANDARD_NET_RUNTIME_NAMES,
|
|
"Slovo std/net.slo must not introduce other compiler-known std names",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_net,
|
|
STANDARD_NET_RUNTIME_NAMES,
|
|
"Glagol local net fixture must not introduce other compiler-known std names",
|
|
);
|
|
for source in [&slovo_net, &glagol_net] {
|
|
assert!(
|
|
!source.contains("dns")
|
|
&& !source.contains("tls")
|
|
&& !source.contains("udp")
|
|
&& !source.contains("async")
|
|
&& !source.contains("http")
|
|
&& !source.contains("timeout")
|
|
&& !source.contains("non_loopback")
|
|
&& !source.contains("host_error"),
|
|
"standard net facade must not claim deferred networking policies"
|
|
);
|
|
}
|
|
for helper in STANDARD_NET_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_net.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/net.slo is missing beta6 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_net.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local net fixture is missing beta6 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let local_json = repo.join("examples/projects/std-layout-local-json/src/json.slo");
|
|
let slovo_json = read(&std_dir.join("json.slo"));
|
|
let glagol_json = read(&local_json);
|
|
assert!(
|
|
slovo_json.contains("(module json") && glagol_json.contains("(module json"),
|
|
"both Slovo std/json.slo and the Glagol local fixture should use explicit `json` module source shape"
|
|
);
|
|
for runtime_name in STANDARD_JSON_RUNTIME_NAMES {
|
|
assert!(
|
|
slovo_json.contains(runtime_name) && glagol_json.contains(runtime_name),
|
|
"standard json facade must stay backed by `{}`",
|
|
runtime_name
|
|
);
|
|
}
|
|
assert_std_only_contains(
|
|
&slovo_json,
|
|
STANDARD_JSON_RUNTIME_NAMES,
|
|
"Slovo std/json.slo must not introduce other compiler-known std names",
|
|
);
|
|
assert_std_only_contains(
|
|
&glagol_json,
|
|
STANDARD_JSON_RUNTIME_NAMES,
|
|
"Glagol local json fixture must not introduce other compiler-known std names",
|
|
);
|
|
for source in [&slovo_json, &glagol_json] {
|
|
assert_deferred_json_surface_absent(source, "standard json facade");
|
|
}
|
|
for helper in STANDARD_JSON_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_json.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/json.slo is missing beta7 facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
glagol_json.contains(&format!("(fn {} ", helper)),
|
|
"Glagol local json fixture is missing beta7 facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_source_shaped_file(path: &Path) {
|
|
let source = read(path);
|
|
assert!(
|
|
source.ends_with('\n'),
|
|
"`{}` must end with a final newline",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
!source.contains('\t'),
|
|
"`{}` must use spaces, not tabs",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
!source
|
|
.lines()
|
|
.any(|line| line.ends_with(' ') || line.ends_with('\t')),
|
|
"`{}` must not contain trailing whitespace",
|
|
path.display()
|
|
);
|
|
}
|
|
|
|
fn assert_source_eq(left: &Path, right: &Path) {
|
|
let left_source = read(left);
|
|
let right_source = read(right);
|
|
|
|
assert_eq!(
|
|
left_source,
|
|
right_source,
|
|
"`{}` and `{}` must stay byte-for-byte aligned",
|
|
left.display(),
|
|
right.display()
|
|
);
|
|
}
|
|
|
|
fn assert_same_supported_body(supported: &Path, formatter: &Path) {
|
|
let supported_body = strip_leading_comments_and_blank_lines(&read(supported));
|
|
let formatter_body = strip_leading_comments_and_blank_lines(&read(formatter));
|
|
|
|
assert_eq!(
|
|
supported_body, formatter_body,
|
|
"formatter canonical body must remain the same current supported program"
|
|
);
|
|
}
|
|
|
|
fn assert_formatter_fixture_contract(path: &Path) {
|
|
let source = read(path);
|
|
|
|
assert!(
|
|
source.starts_with("; status: formatter-canonical\n"),
|
|
"`{}` must declare formatter-only status",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
source.ends_with('\n'),
|
|
"`{}` must end with a final newline",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
!source
|
|
.lines()
|
|
.any(|line| line.ends_with(' ') || line.ends_with('\t')),
|
|
"`{}` must not contain trailing whitespace",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
!source.contains('\t'),
|
|
"`{}` must use spaces, not tabs",
|
|
path.display()
|
|
);
|
|
|
|
let code = strip_comments(&source);
|
|
let forbidden_forms = [
|
|
"if", "let", "var", "set", "while", "struct", "test", "unsafe", "string", "array", "slice",
|
|
"option", "result", "ptr",
|
|
];
|
|
|
|
for form in forbidden_forms {
|
|
assert!(
|
|
!contains_word(&code, form),
|
|
"formatter canonical fixture contains a form outside the supported add fixture surface: `{}`",
|
|
form
|
|
);
|
|
}
|
|
assert!(
|
|
!code.contains('"'),
|
|
"formatter canonical fixture must not contain string literals"
|
|
);
|
|
}
|
|
|
|
fn assert_compiler_output_matches_supported_add_shape(repo: &Path, fixture: &Path) {
|
|
let expected = read(&repo.join("tests/add.expected.ll"));
|
|
let output = run_glagol([fixture.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&output.stdout);
|
|
let stderr = String::from_utf8_lossy(&output.stderr);
|
|
|
|
assert!(
|
|
output.status.success(),
|
|
"compiler rejected supported add fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for accepted add fixture:\n{}",
|
|
stderr
|
|
);
|
|
assert!(
|
|
!stdout.contains("panicked at") && !stderr.contains("panicked at"),
|
|
"compiler panicked for supported add fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
|
|
for required in required_llvm_shapes(&expected) {
|
|
assert!(
|
|
stdout.contains(required),
|
|
"LLVM output did not contain expected shape `{}`\nstdout:\n{}",
|
|
required,
|
|
stdout
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_tree_printer_matches_fixture(repo: &Path, fixture: &Path) {
|
|
let expected = read(&repo.join("tests/add.sexpr"));
|
|
let output = run_glagol([OsStr::new("--print-tree"), fixture.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&output.stdout);
|
|
let stderr = String::from_utf8_lossy(&output.stderr);
|
|
|
|
assert!(
|
|
output.status.success(),
|
|
"tree printer rejected supported add fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert_eq!(stdout, expected, "tree printer fixture drifted");
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"tree printer wrote stderr for accepted add fixture:\n{}",
|
|
stderr
|
|
);
|
|
}
|
|
|
|
fn assert_formatter_matches_fixture(fixture: &Path) {
|
|
let expected = read(fixture);
|
|
let output = run_glagol([OsStr::new("--format"), fixture.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&output.stdout);
|
|
let stderr = String::from_utf8_lossy(&output.stderr);
|
|
|
|
assert!(
|
|
output.status.success(),
|
|
"formatter rejected supported fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert_eq!(stdout, expected, "formatter fixture drifted");
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"formatter wrote stderr for accepted fixture:\n{}",
|
|
stderr
|
|
);
|
|
}
|
|
|
|
fn assert_lowering_inspector_matches_fixture(
|
|
repo: &Path,
|
|
fixture: &Path,
|
|
mode: &str,
|
|
snapshot: &str,
|
|
) {
|
|
let expected = read(&repo.join("tests").join(snapshot));
|
|
let output = run_glagol([OsStr::new(mode), fixture.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&output.stdout);
|
|
let stderr = String::from_utf8_lossy(&output.stderr);
|
|
|
|
assert!(
|
|
output.status.success(),
|
|
"lowering inspector `{}` rejected supported fixture\nstdout:\n{}\nstderr:\n{}",
|
|
mode,
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert_eq!(
|
|
stdout, expected,
|
|
"lowering inspector `{}` fixture drifted",
|
|
mode
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"lowering inspector `{}` wrote stderr for accepted fixture:\n{}",
|
|
mode,
|
|
stderr
|
|
);
|
|
}
|
|
|
|
fn assert_lowering_inspector_matrix_matches_fixtures(repo: &Path) {
|
|
for case in LOWERING_INSPECTOR_CASES {
|
|
let source = repo.join(case.source);
|
|
assert_lowering_inspector_matches_fixture(
|
|
repo,
|
|
&source,
|
|
"--inspect-lowering=surface",
|
|
case.surface_snapshot,
|
|
);
|
|
assert_lowering_inspector_matches_fixture(
|
|
repo,
|
|
&source,
|
|
"--inspect-lowering=checked",
|
|
case.checked_snapshot,
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_top_level_test_tooling_matches_fixtures(repo: &Path) {
|
|
let fixture = repo.join("tests/top-level-test.slo");
|
|
|
|
let expected_tree = read(&repo.join("tests/top-level-test.sexpr"));
|
|
let tree = run_glagol([OsStr::new("--print-tree"), fixture.as_os_str()]);
|
|
assert_success_stdout(tree, &expected_tree, "top-level test tree fixture");
|
|
|
|
assert_lowering_inspector_matches_fixture(
|
|
repo,
|
|
&fixture,
|
|
"--inspect-lowering=surface",
|
|
"top-level-test.surface.lower",
|
|
);
|
|
assert_lowering_inspector_matches_fixture(
|
|
repo,
|
|
&fixture,
|
|
"--inspect-lowering=checked",
|
|
"top-level-test.checked.lower",
|
|
);
|
|
|
|
let checked = run_glagol([OsStr::new("--check-tests"), fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
checked,
|
|
"test \"add works\" ... checked\n1 test(s) checked\n",
|
|
"top-level test checker output",
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
"test \"add works\" ... ok\n1 test(s) passed\n",
|
|
"top-level test runner output",
|
|
);
|
|
|
|
let compile = run_glagol([fixture.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected top-level test fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @add") && stdout.contains("define i32 @main"),
|
|
"compiler output for top-level test fixture lost function emission\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("add works"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for top-level test fixture:\n{}",
|
|
stderr
|
|
);
|
|
}
|
|
|
|
fn assert_array_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected array fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @immediate_second()")
|
|
&& stdout.contains("insertvalue [3 x i32]")
|
|
&& stdout.contains("extractvalue [3 x i32]")
|
|
&& stdout.contains("%values.addr = alloca [3 x i32]")
|
|
&& stdout.contains("getelementptr inbounds [3 x i32]")
|
|
&& stdout.contains("load i32"),
|
|
"compiler output for array fixture lost index shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("immediate array index") && !stdout.contains("array local index"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for array fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"immediate array index\" ... ok\n",
|
|
"test \"array local index\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"array test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "array formatter output");
|
|
}
|
|
|
|
fn assert_array_direct_scalars_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected direct-scalar array fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @i32_second()")
|
|
&& stdout.contains("define i64 @i64_local_pick()")
|
|
&& stdout.contains("define double @f64_third()")
|
|
&& stdout.contains("define i1 @bool_local_pick()")
|
|
&& stdout.contains("insertvalue [3 x i32]")
|
|
&& stdout.contains("insertvalue [3 x double]")
|
|
&& stdout.contains("alloca [3 x i64]")
|
|
&& stdout.contains("alloca [3 x i1]"),
|
|
"compiler output for direct-scalar array fixture lost widened array shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("i32 direct scalar array index")
|
|
&& !stdout.contains("bool local direct scalar array index"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for direct-scalar array fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"i32 direct scalar array index\" ... ok\n",
|
|
"test \"i64 local direct scalar array index\" ... ok\n",
|
|
"test \"f64 direct scalar array index\" ... ok\n",
|
|
"test \"bool local direct scalar array index\" ... ok\n",
|
|
"4 test(s) passed\n",
|
|
),
|
|
"direct-scalar array test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"direct-scalar array formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_array_string_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected string-array fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define ptr @immediate_second()")
|
|
&& stdout.contains("define ptr @local_pick()")
|
|
&& stdout.contains("insertvalue [3 x ptr]")
|
|
&& stdout.contains("alloca [3 x ptr]"),
|
|
"compiler output for string-array fixture lost widened array shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("string immediate array index")
|
|
&& !stdout.contains("string local array index"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for string-array fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"string immediate array index\" ... ok\n",
|
|
"test \"string local array index\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"string-array test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "string-array formatter output");
|
|
}
|
|
|
|
fn assert_array_value_flow_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected array value-flow fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define [3 x i32] @make_values(i32 %base)")
|
|
&& stdout.contains("define i32 @at([3 x i32] %values, i32 %i)")
|
|
&& stdout.contains("define i32 @parameter_local_copy([3 x i32] %values, i32 %i)")
|
|
&& stdout.contains("call [3 x i32] @make_values(i32 20)")
|
|
&& stdout.contains("call i32 @at([3 x i32]")
|
|
&& stdout.contains("call void @__glagol_array_bounds_trap()")
|
|
&& stdout.contains("array.index.trap")
|
|
&& stdout.contains("getelementptr inbounds [3 x i32]"),
|
|
"compiler output for array value-flow fixture lost value-flow or bounds-check shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("array parameter value flow")
|
|
&& !stdout.contains("array dynamic index")
|
|
&& !stdout.contains("array parameter local copy"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for array value-flow fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"array parameter value flow\" ... ok\n",
|
|
"test \"array dynamic index\" ... ok\n",
|
|
"test \"array local call value flow\" ... ok\n",
|
|
"test \"array parameter local copy\" ... ok\n",
|
|
"test \"array return call value flow\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
"array value-flow test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"array value-flow formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_array_direct_scalars_value_flow_tooling_matches_fixtures(
|
|
example: &Path,
|
|
formatter_fixture: &Path,
|
|
) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected direct-scalar array value-flow fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define [3 x i32] @make_i32_values(i32 %base)")
|
|
&& stdout.contains("define [3 x i64] @make_i64_values(i64 %base)")
|
|
&& stdout.contains("define [3 x double] @make_f64_values(double %base)")
|
|
&& stdout.contains("define [3 x i1] @make_flags(i1 %first)")
|
|
&& stdout.contains("define i64 @i64_at([3 x i64] %values, i32 %i)")
|
|
&& stdout.contains("define double @f64_at([3 x double] %values, i32 %i)")
|
|
&& stdout.contains("define [3 x i1] @echo_flags([3 x i1] %values)")
|
|
&& stdout.contains("call void @__glagol_array_bounds_trap()")
|
|
&& stdout.contains("array.index.trap")
|
|
&& stdout.contains("getelementptr inbounds [3 x i64]")
|
|
&& stdout.contains("getelementptr inbounds [3 x double]"),
|
|
"compiler output for direct-scalar array value-flow fixture lost value-flow or bounds-check shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("i64 array local call value flow")
|
|
&& !stdout.contains("bool array dynamic index"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for direct-scalar array value-flow fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"i32 array parameter value flow\" ... ok\n",
|
|
"test \"i64 array local call value flow\" ... ok\n",
|
|
"test \"f64 array parameter local copy\" ... ok\n",
|
|
"test \"bool array dynamic index\" ... ok\n",
|
|
"test \"bool array return call value flow\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
"direct-scalar array value-flow test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"direct-scalar array value-flow formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_array_string_value_flow_tooling_matches_fixtures(
|
|
example: &Path,
|
|
formatter_fixture: &Path,
|
|
) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected string-array value-flow fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define [3 x ptr] @make_words(ptr %head)")
|
|
&& stdout.contains("define ptr @at([3 x ptr] %values, i32 %i)")
|
|
&& stdout.contains("define [3 x ptr] @echo([3 x ptr] %values)")
|
|
&& stdout.contains("call void @__glagol_array_bounds_trap()")
|
|
&& stdout.contains("array.index.trap")
|
|
&& stdout.contains("getelementptr inbounds [3 x ptr]"),
|
|
"compiler output for string-array value-flow fixture lost value-flow or bounds-check shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("string array local call value flow")
|
|
&& !stdout.contains("string array dynamic index"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for string-array value-flow fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"string array parameter value flow\" ... ok\n",
|
|
"test \"string array dynamic index\" ... ok\n",
|
|
"test \"string array local call value flow\" ... ok\n",
|
|
"test \"string array parameter local copy\" ... ok\n",
|
|
"test \"string array return call value flow\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
"string-array value-flow test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"string-array value-flow formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_local_variable_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected local-variable fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @add_local")
|
|
&& stdout.contains("%total.addr = alloca i32")
|
|
&& stdout.contains("add i32 %a, 1")
|
|
&& stdout.contains("store i32")
|
|
&& stdout.contains("load i32")
|
|
&& stdout.contains("define i1 @keep_flag(i1 %flag)")
|
|
&& !stdout.contains("%local_flag.addr = alloca i1")
|
|
&& stdout.contains("define i1 @flip_flag(i1 %flag)")
|
|
&& stdout.contains("%current.addr = alloca i1")
|
|
&& stdout.contains("%count.addr = alloca i64")
|
|
&& stdout.contains("%amount.addr = alloca double"),
|
|
"compiler output for local-variable fixture lost local value/storage shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("locals work")
|
|
&& !stdout.contains("bool let locals work")
|
|
&& !stdout.contains("bool let locals preserve false")
|
|
&& !stdout.contains("bool var set flips true")
|
|
&& !stdout.contains("bool var set flips false")
|
|
&& !stdout.contains("i64 var set works")
|
|
&& !stdout.contains("f64 var set works"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for local-variable fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"locals work\" ... ok\n",
|
|
"test \"bool let locals work\" ... ok\n",
|
|
"test \"bool let locals preserve false\" ... ok\n",
|
|
"test \"bool var set flips true\" ... ok\n",
|
|
"test \"bool var set flips false\" ... ok\n",
|
|
"test \"i64 var set works\" ... ok\n",
|
|
"test \"f64 var set works\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
"local-variable test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "local-variable formatter output");
|
|
}
|
|
|
|
fn assert_option_result_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected option/result fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define { i1, i32 } @maybe_value()")
|
|
&& stdout.contains("define { i1, i32 } @maybe_empty()")
|
|
&& stdout.contains("define { i1, i32 } @result_ok()")
|
|
&& stdout.contains("define { i1, i32 } @result_err()")
|
|
&& stdout.contains("insertvalue { i1, i32 } undef, i1 1, 0")
|
|
&& stdout.contains("insertvalue { i1, i32 } undef, i1 0, 0")
|
|
&& stdout.contains("ret { i1, i32 } %")
|
|
&& !stdout.contains("define ptr @maybe_value")
|
|
&& !stdout.contains("define ptr @result_ok"),
|
|
"compiler output for option/result fixture lost aggregate shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for option/result fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "option/result formatter output");
|
|
}
|
|
|
|
fn assert_option_result_flow_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected option/result flow fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @option_score({ i1, i32 } %value)")
|
|
&& stdout.contains("define i32 @option_wide_score({ i1, i64 } %value)")
|
|
&& stdout.contains("define i32 @option_string_score({ i1, ptr } %value)")
|
|
&& stdout.contains("define i32 @result_success_score({ i1, i32 } %value)")
|
|
&& stdout.contains("%value.addr = alloca { i1, i32 }")
|
|
&& stdout.contains("%value.addr = alloca { i1, ptr }")
|
|
&& stdout.contains("call { i1, i64 } @maybe_wide_value(i64 2147483648)")
|
|
&& stdout.contains("call { i1, i32 } @maybe_value(i32 42)")
|
|
&& stdout.contains("call { i1, ptr } @maybe_string_value(ptr @.str.")
|
|
&& stdout.contains("extractvalue { i1, i32 } %")
|
|
&& stdout.contains("extractvalue { i1, ptr } %")
|
|
&& stdout.contains("extractvalue { i1, i64 } %")
|
|
&& stdout.contains("xor i1 %"),
|
|
"compiler output for option/result flow fixture lost value-flow shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for option/result flow fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"option local value flow\" ... ok\n",
|
|
"test \"option call observation\" ... ok\n",
|
|
"test \"option i64 local value flow\" ... ok\n",
|
|
"test \"option i64 call observation\" ... ok\n",
|
|
"test \"option f64 local value flow\" ... ok\n",
|
|
"test \"option f64 call observation\" ... ok\n",
|
|
"test \"option bool local value flow\" ... ok\n",
|
|
"test \"option bool call observation\" ... ok\n",
|
|
"test \"option string local value flow\" ... ok\n",
|
|
"test \"option string call observation\" ... ok\n",
|
|
"test \"result call observation\" ... ok\n",
|
|
"test \"result local value flow\" ... ok\n",
|
|
"12 test(s) passed\n",
|
|
),
|
|
"option/result flow test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"option/result flow formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_option_result_match_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected option/result match fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @option_value_or({ i1, i32 } %value, i32 %fallback)")
|
|
&& stdout.contains("define i32 @option_bump_or_zero({ i1, i32 } %value)")
|
|
&& stdout
|
|
.contains("define ptr @option_string_value_or({ i1, ptr } %value, ptr %fallback)")
|
|
&& stdout.contains(
|
|
"define ptr @option_string_selected_or({ i1, ptr } %value, ptr %fallback)"
|
|
)
|
|
&& stdout.contains("define i32 @result_value_or_code({ i1, i32 } %value)")
|
|
&& stdout.contains("define i32 @result_score({ i1, i32 } %value)")
|
|
&& stdout.contains("match.some")
|
|
&& stdout.contains("match.none")
|
|
&& stdout.contains("match.ok")
|
|
&& stdout.contains("match.err")
|
|
&& stdout.contains(" phi i32 ")
|
|
&& stdout.contains(" phi ptr "),
|
|
"compiler output for option/result match fixture lost branch shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for option/result match fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"option match some payload\" ... ok\n",
|
|
"test \"option match none fallback\" ... ok\n",
|
|
"test \"option match multi expression arm\" ... ok\n",
|
|
"test \"option i64 match some payload\" ... ok\n",
|
|
"test \"option i64 match none fallback\" ... ok\n",
|
|
"test \"option i64 match multi expression arm\" ... ok\n",
|
|
"test \"option f64 match some payload\" ... ok\n",
|
|
"test \"option f64 match none fallback\" ... ok\n",
|
|
"test \"option f64 match multi expression arm\" ... ok\n",
|
|
"test \"option bool match some payload\" ... ok\n",
|
|
"test \"option bool match none fallback\" ... ok\n",
|
|
"test \"option bool match multi expression arm\" ... ok\n",
|
|
"test \"option string match some payload\" ... ok\n",
|
|
"test \"option string match none fallback\" ... ok\n",
|
|
"test \"option string match multi expression arm\" ... ok\n",
|
|
"test \"result match ok payload\" ... ok\n",
|
|
"test \"result match err payload\" ... ok\n",
|
|
"test \"result match computed arm\" ... ok\n",
|
|
"18 test(s) passed\n",
|
|
),
|
|
"option/result match test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"option/result match formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_option_result_payload_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected option/result payload fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @option_direct_payload()")
|
|
&& stdout.contains("define i32 @option_param_payload({ i1, i32 } %value)")
|
|
&& stdout.contains("define i32 @option_local_payload()")
|
|
&& stdout.contains("define i32 @option_call_payload()")
|
|
&& stdout.contains("define i32 @option_guarded_payload({ i1, i32 } %value)")
|
|
&& stdout.contains("define i32 @result_ok_direct_payload()")
|
|
&& stdout.contains("define i32 @result_err_direct_payload()")
|
|
&& stdout.contains("define i32 @result_ok_param_payload({ i1, i32 } %value)")
|
|
&& stdout.contains("define i32 @result_err_param_payload({ i1, i32 } %value)")
|
|
&& stdout.contains("define i32 @result_ok_local_payload()")
|
|
&& stdout.contains("define i32 @result_err_call_payload()")
|
|
&& stdout.contains("call void @__glagol_unwrap_some_trap()")
|
|
&& stdout.contains("call void @__glagol_unwrap_ok_trap()")
|
|
&& stdout.contains("call void @__glagol_unwrap_err_trap()")
|
|
&& stdout.contains("unwrap.trap")
|
|
&& stdout.contains("if.then")
|
|
&& stdout.contains(" phi i32 ")
|
|
&& stdout.contains("extractvalue { i1, i32 } %"),
|
|
"compiler output for option/result payload fixture lost payload-access shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for option/result payload fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"unwrap some direct constructor\" ... ok\n",
|
|
"test \"unwrap some local\" ... ok\n",
|
|
"test \"unwrap some call\" ... ok\n",
|
|
"test \"unwrap some parameter\" ... ok\n",
|
|
"test \"guarded unwrap some present\" ... ok\n",
|
|
"test \"guarded unwrap some absent\" ... ok\n",
|
|
"test \"unwrap some i64 direct constructor\" ... ok\n",
|
|
"test \"unwrap some i64 local\" ... ok\n",
|
|
"test \"unwrap some i64 call\" ... ok\n",
|
|
"test \"unwrap some i64 parameter\" ... ok\n",
|
|
"test \"guarded unwrap some i64 present\" ... ok\n",
|
|
"test \"guarded unwrap some i64 absent\" ... ok\n",
|
|
"test \"unwrap some f64 direct constructor\" ... ok\n",
|
|
"test \"unwrap some f64 local\" ... ok\n",
|
|
"test \"unwrap some f64 call\" ... ok\n",
|
|
"test \"unwrap some f64 parameter\" ... ok\n",
|
|
"test \"guarded unwrap some f64 present\" ... ok\n",
|
|
"test \"guarded unwrap some f64 absent\" ... ok\n",
|
|
"test \"unwrap some bool direct constructor\" ... ok\n",
|
|
"test \"unwrap some bool local\" ... ok\n",
|
|
"test \"unwrap some bool call\" ... ok\n",
|
|
"test \"unwrap some bool parameter\" ... ok\n",
|
|
"test \"guarded unwrap some bool present\" ... ok\n",
|
|
"test \"guarded unwrap some bool absent\" ... ok\n",
|
|
"test \"unwrap some string direct constructor\" ... ok\n",
|
|
"test \"unwrap some string local\" ... ok\n",
|
|
"test \"unwrap some string call\" ... ok\n",
|
|
"test \"unwrap some string parameter\" ... ok\n",
|
|
"test \"guarded unwrap some string present\" ... ok\n",
|
|
"test \"guarded unwrap some string absent\" ... ok\n",
|
|
"test \"unwrap ok direct constructor\" ... ok\n",
|
|
"test \"unwrap err direct constructor\" ... ok\n",
|
|
"test \"unwrap ok parameter\" ... ok\n",
|
|
"test \"unwrap err parameter\" ... ok\n",
|
|
"test \"unwrap ok local\" ... ok\n",
|
|
"test \"unwrap err call\" ... ok\n",
|
|
"36 test(s) passed\n",
|
|
),
|
|
"option/result payload test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"option/result payload formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_enum_struct_field_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected enum struct field fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define { i32, { i32, i32 } } @make_tagged")
|
|
&& stdout.contains("extractvalue { i32, { i32, i32 } }")
|
|
&& stdout.contains("switch i32")
|
|
&& stdout.contains("and i1"),
|
|
"compiler output for enum struct field fixture lost aggregate/match shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for enum struct field fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"enum struct field payloadless equality\" ... ok\n",
|
|
"test \"enum struct field unary payload equality\" ... ok\n",
|
|
"test \"enum struct field access return\" ... ok\n",
|
|
"test \"enum struct field local param return call flow\" ... ok\n",
|
|
"test \"enum struct field match missing\" ... ok\n",
|
|
"test \"enum struct field status predicate\" ... ok\n",
|
|
"6 test(s) passed\n",
|
|
),
|
|
"enum struct field test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"enum struct field formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_primitive_struct_field_tooling_matches_fixtures(
|
|
example: &Path,
|
|
formatter_fixture: &Path,
|
|
) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected primitive struct field fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define { i32, i1, ptr } @make_record")
|
|
&& stdout.contains("insertvalue { i32, i1, ptr }")
|
|
&& stdout.contains("extractvalue { i32, i1, ptr }")
|
|
&& stdout.contains("call i1 @__glagol_string_eq")
|
|
&& stdout.contains("call i32 @string_len"),
|
|
"compiler output for primitive struct field fixture lost aggregate/string shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for primitive struct field fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"primitive struct i32 field access\" ... ok\n",
|
|
"test \"primitive struct bool field predicate\" ... ok\n",
|
|
"test \"primitive struct bool field false branch\" ... ok\n",
|
|
"test \"primitive struct string field equality\" ... ok\n",
|
|
"test \"primitive struct string field length\" ... ok\n",
|
|
"test \"primitive struct local param return call flow\" ... ok\n",
|
|
"test \"primitive struct string field access return\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
"primitive struct field test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"primitive struct field formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_numeric_struct_field_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected numeric struct field fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define { i64, double } @make_record")
|
|
&& stdout.contains("insertvalue { i64, double }")
|
|
&& stdout.contains("extractvalue { i64, double }")
|
|
&& stdout.contains("add i64")
|
|
&& stdout.contains("fadd double"),
|
|
"compiler output for numeric struct field fixture lost aggregate/numeric shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for numeric struct field fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"numeric struct i64 field access\" ... ok\n",
|
|
"test \"numeric struct f64 field access\" ... ok\n",
|
|
"test \"numeric struct i64 arithmetic after access\" ... ok\n",
|
|
"test \"numeric struct f64 arithmetic after access\" ... ok\n",
|
|
"test \"numeric struct i64 comparison after access\" ... ok\n",
|
|
"test \"numeric struct f64 comparison after access\" ... ok\n",
|
|
"test \"numeric struct local param return call flow\" ... ok\n",
|
|
"test \"numeric struct i64 format after access\" ... ok\n",
|
|
"test \"numeric struct f64 format after access\" ... ok\n",
|
|
"9 test(s) passed\n",
|
|
),
|
|
"numeric struct field test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"numeric struct field formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_string_print_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"string-print fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare void @print_string(ptr)")
|
|
&& stdout.contains(
|
|
"@.str.0 = private unnamed_addr constant [6 x i8] c\"hello\\00\", align 1",
|
|
)
|
|
&& stdout.contains(
|
|
"@.str.1 = private unnamed_addr constant [22 x i8] c\"line\\0Aquote\\22slash\\5Ctab\\09\\00\", align 1",
|
|
)
|
|
&& stdout.contains("call void @print_string(ptr @.str.0)")
|
|
&& stdout.contains("call void @print_string(ptr @.str.1)"),
|
|
"string-print fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"string-print fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "string-print formatter output");
|
|
}
|
|
|
|
fn assert_print_bool_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"print-bool fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare void @print_bool(i1)")
|
|
&& stdout.contains("declare i1 @__glagol_string_eq(ptr, ptr)")
|
|
&& stdout.contains("call void @print_bool(i1 1)")
|
|
&& stdout.contains("call void @print_bool(i1 0)")
|
|
&& stdout.contains("call i1 @__glagol_string_eq(ptr @.str.0, ptr @.str.0)"),
|
|
"print-bool fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"print-bool fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "print-bool formatter output");
|
|
}
|
|
|
|
fn assert_random_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"random fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare i32 @__glagol_random_i32()")
|
|
&& stdout.contains("call i32 @__glagol_random_i32()")
|
|
&& stdout.contains("declare void @print_bool(i1)")
|
|
&& !stdout.contains("@std.random"),
|
|
"random fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"random fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"random i32 is non-negative\" ... ok\n",
|
|
"1 test(s) passed\n",
|
|
),
|
|
"random test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "random formatter output");
|
|
}
|
|
|
|
fn assert_stdin_result_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"stdin-result fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare ptr @__glagol_io_read_stdin_result()")
|
|
&& stdout.contains("call ptr @__glagol_io_read_stdin_result()")
|
|
&& !stdout.contains("@std.io.read_stdin_result"),
|
|
"stdin-result fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"stdin-result fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"stdin result test runner returns ok\" ... ok\n",
|
|
"test \"stdin result payload length matches match\" ... ok\n",
|
|
"test \"stdin result match observes ok payload\" ... ok\n",
|
|
"3 test(s) passed\n",
|
|
),
|
|
"stdin-result test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "stdin-result formatter output");
|
|
}
|
|
|
|
fn assert_string_parse_i32_result_tooling_matches_fixtures(
|
|
example: &Path,
|
|
formatter_fixture: &Path,
|
|
) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"string-parse-i32-result fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare i64 @__glagol_string_parse_i32_result(ptr)")
|
|
&& stdout.contains("call i64 @__glagol_string_parse_i32_result(ptr ")
|
|
&& stdout.contains("declare ptr @__glagol_io_read_stdin_result()")
|
|
&& stdout.contains("call ptr @__glagol_io_read_stdin_result()")
|
|
&& stdout.contains("define { i1, i32 } @parse_text(ptr %text)")
|
|
&& stdout.contains("define { i1, i32 } @parse_stdin_text()")
|
|
&& stdout.contains("lshr i64")
|
|
&& stdout.contains("trunc i64")
|
|
&& stdout.contains("insertvalue { i1, i32 }")
|
|
&& !stdout.contains("@std.string.parse_i32_result"),
|
|
"string-parse-i32-result fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"string-parse-i32-result fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"parse 42 ok\" ... ok\n",
|
|
"test \"parse negative 7 ok\" ... ok\n",
|
|
"test \"parse empty err\" ... ok\n",
|
|
"test \"parse trailing byte err\" ... ok\n",
|
|
"test \"parse overflow err\" ... ok\n",
|
|
"test \"parse stdin text structurally\" ... ok\n",
|
|
"6 test(s) passed\n",
|
|
),
|
|
"string-parse-i32-result test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"string-parse-i32-result formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_string_parse_i64_result_tooling_matches_fixtures(
|
|
example: &Path,
|
|
formatter_fixture: &Path,
|
|
) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"string-parse-i64-result fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare i32 @__glagol_string_parse_i64_result(ptr, ptr)")
|
|
&& stdout.contains("call i32 @__glagol_string_parse_i64_result(ptr ")
|
|
&& stdout.contains("define { i1, i64, i32 } @parse_i64(ptr %text)")
|
|
&& stdout.contains("alloca i64")
|
|
&& stdout.contains("insertvalue { i1, i64, i32 }")
|
|
&& stdout.contains("extractvalue { i1, i64, i32 }")
|
|
&& stdout.contains("call ptr @__glagol_num_i64_to_string(i64 ")
|
|
&& !stdout.contains("@std.string.parse_i64_result"),
|
|
"string-parse-i64-result fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"string-parse-i64-result fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"parse i64 zero ok\" ... ok\n",
|
|
"test \"parse i64 negative ok\" ... ok\n",
|
|
"test \"parse i64 low ok\" ... ok\n",
|
|
"test \"parse i64 high ok\" ... ok\n",
|
|
"test \"parse i64 empty err\" ... ok\n",
|
|
"test \"parse i64 plus err\" ... ok\n",
|
|
"test \"parse i64 above range err\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
"string-parse-i64-result test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"string-parse-i64-result formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_string_parse_f64_result_tooling_matches_fixtures(
|
|
example: &Path,
|
|
formatter_fixture: &Path,
|
|
) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"string-parse-f64-result fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare i32 @__glagol_string_parse_f64_result(ptr, ptr)")
|
|
&& stdout.contains("call i32 @__glagol_string_parse_f64_result(ptr ")
|
|
&& stdout.contains("define { i1, double, i32 } @parse_f64(ptr %text)")
|
|
&& stdout.contains("alloca double")
|
|
&& stdout.contains("insertvalue { i1, double, i32 }")
|
|
&& stdout.contains("extractvalue { i1, double, i32 }")
|
|
&& !stdout.contains("@std.string.parse_f64_result"),
|
|
"string-parse-f64-result fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"string-parse-f64-result fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"parse f64 decimal ok\" ... ok\n",
|
|
"test \"parse f64 negative decimal ok\" ... ok\n",
|
|
"test \"parse f64 text err\" ... ok\n",
|
|
"test \"parse f64 nan err\" ... ok\n",
|
|
"4 test(s) passed\n",
|
|
),
|
|
"string-parse-f64-result test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"string-parse-f64-result formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_result_f64_bool_source_flow_matches_fixture(example: &Path) {
|
|
let format = run_glagol([
|
|
OsStr::new("fmt"),
|
|
OsStr::new("--check"),
|
|
example.as_os_str(),
|
|
]);
|
|
assert_success_stdout(format, "", "result f64 bool source flow fmt --check");
|
|
|
|
let check = run_glagol([OsStr::new("check"), example.as_os_str()]);
|
|
assert_success_stdout(check, "", "result f64 bool source flow check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"result f64 ok constructor and match\" ... ok\n",
|
|
"test \"result f64 err constructor and match\" ... ok\n",
|
|
"test \"result bool ok constructor and match\" ... ok\n",
|
|
"test \"result bool err constructor and match\" ... ok\n",
|
|
"4 test(s) passed\n",
|
|
),
|
|
"result f64 bool source flow test",
|
|
);
|
|
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"result f64 bool source flow compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("insertvalue { i1, double, i32 }")
|
|
&& stdout.contains("insertvalue { i1, i1, i32 }")
|
|
&& stdout.contains("extractvalue { i1, double, i32 }")
|
|
&& stdout.contains("extractvalue { i1, i1, i32 }"),
|
|
"result f64 bool source flow LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
}
|
|
|
|
fn assert_integer_remainder_tooling_matches_fixture(example: &Path) {
|
|
let format = run_glagol([
|
|
OsStr::new("fmt"),
|
|
OsStr::new("--check"),
|
|
example.as_os_str(),
|
|
]);
|
|
assert_success_stdout(format, "", "integer remainder fmt --check");
|
|
|
|
let check = run_glagol([OsStr::new("check"), example.as_os_str()]);
|
|
assert_success_stdout(check, "", "integer remainder check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"i32 remainder\" ... ok\n",
|
|
"test \"i32 signed remainder\" ... ok\n",
|
|
"test \"i64 remainder\" ... ok\n",
|
|
"test \"i64 signed remainder\" ... ok\n",
|
|
"test \"integer remainder summary\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
"integer remainder test",
|
|
);
|
|
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"integer remainder compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("srem i32") && stdout.contains("srem i64"),
|
|
"integer remainder LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"integer remainder compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
}
|
|
|
|
fn assert_boolean_logic_tooling_matches_fixture(example: &Path) {
|
|
let format = run_glagol([
|
|
OsStr::new("fmt"),
|
|
OsStr::new("--check"),
|
|
example.as_os_str(),
|
|
]);
|
|
assert_success_stdout(format, "", "boolean logic fmt --check");
|
|
|
|
let check = run_glagol([OsStr::new("check"), example.as_os_str()]);
|
|
assert_success_stdout(check, "", "boolean logic check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"and true\" ... ok\n",
|
|
"test \"and false\" ... ok\n",
|
|
"test \"or true\" ... ok\n",
|
|
"test \"not false\" ... ok\n",
|
|
"test \"and short circuit\" ... ok\n",
|
|
"test \"or short circuit\" ... ok\n",
|
|
"test \"boolean logic summary\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
"boolean logic test",
|
|
);
|
|
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"boolean logic compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i1 @and_true()")
|
|
&& stdout.contains("define i1 @and_short_circuits()")
|
|
&& stdout.contains("br i1"),
|
|
"boolean logic LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"boolean logic compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
}
|
|
|
|
fn assert_integer_bitwise_tooling_matches_fixture(example: &Path) {
|
|
let format = run_glagol([
|
|
OsStr::new("fmt"),
|
|
OsStr::new("--check"),
|
|
example.as_os_str(),
|
|
]);
|
|
assert_success_stdout(format, "", "integer bitwise fmt --check");
|
|
|
|
let check = run_glagol([OsStr::new("check"), example.as_os_str()]);
|
|
assert_success_stdout(check, "", "integer bitwise check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"i32 bit and\" ... ok\n",
|
|
"test \"i32 bit or\" ... ok\n",
|
|
"test \"i32 bit xor\" ... ok\n",
|
|
"test \"i64 bit and\" ... ok\n",
|
|
"test \"i64 bit or\" ... ok\n",
|
|
"test \"i64 bit xor\" ... ok\n",
|
|
"test \"integer bitwise summary\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
"integer bitwise test",
|
|
);
|
|
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"integer bitwise compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("and i32")
|
|
&& stdout.contains("or i32")
|
|
&& stdout.contains("xor i32")
|
|
&& stdout.contains("and i64")
|
|
&& stdout.contains("or i64")
|
|
&& stdout.contains("xor i64"),
|
|
"integer bitwise LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"integer bitwise compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
}
|
|
|
|
fn assert_string_parse_bool_result_tooling_matches_fixtures(
|
|
example: &Path,
|
|
formatter_fixture: &Path,
|
|
) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"string-parse-bool-result fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare i32 @__glagol_string_parse_bool_result(ptr, ptr)")
|
|
&& stdout.contains("call i32 @__glagol_string_parse_bool_result(ptr ")
|
|
&& stdout.contains("define { i1, i1, i32 } @parse_bool(ptr %text)")
|
|
&& stdout.contains("define i32 @bool_score(ptr %text)")
|
|
&& stdout.contains("alloca i1")
|
|
&& stdout.contains("insertvalue { i1, i1, i32 }")
|
|
&& stdout.contains("extractvalue { i1, i1, i32 }")
|
|
&& !stdout.contains("@std.string.parse_bool_result"),
|
|
"string-parse-bool-result fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"string-parse-bool-result fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"parse bool true ok\" ... ok\n",
|
|
"test \"parse bool false ok\" ... ok\n",
|
|
"test \"parse bool uppercase err\" ... ok\n",
|
|
"test \"parse bool empty err\" ... ok\n",
|
|
"test \"parse bool whitespace err\" ... ok\n",
|
|
"test \"parse bool helper flow\" ... ok\n",
|
|
"6 test(s) passed\n",
|
|
),
|
|
"string-parse-bool-result test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"string-parse-bool-result formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_f64_to_string_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"f64-to-string fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare ptr @__glagol_num_f64_to_string(double)")
|
|
&& stdout.contains("call ptr @__glagol_num_f64_to_string(double ")
|
|
&& stdout.contains("call void @print_string(ptr %")
|
|
&& !stdout.contains("@std.num.f64_to_string"),
|
|
"f64-to-string fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"f64-to-string fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"f64 zero to string\" ... ok\n",
|
|
"test \"f64 fractional to string\" ... ok\n",
|
|
"test \"f64 negative to string\" ... ok\n",
|
|
"test \"f64 whole to string\" ... ok\n",
|
|
"test \"f64 negative string length\" ... ok\n",
|
|
"test \"f64 whole string length\" ... ok\n",
|
|
"6 test(s) passed\n",
|
|
),
|
|
"f64-to-string test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "f64-to-string formatter output");
|
|
}
|
|
|
|
fn assert_f64_to_i32_result_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"f64-to-i32-result fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("fcmp oge double")
|
|
&& stdout.contains("fcmp ole double")
|
|
&& stdout.contains("f64.to_i32.integral")
|
|
&& stdout.contains("f64.to_i32.exponent")
|
|
&& stdout.contains("f64.to_i32.fraction")
|
|
&& stdout.contains("bitcast double")
|
|
&& stdout.contains("lshr i64")
|
|
&& stdout.contains("fptosi double")
|
|
&& !stdout.contains("frem double")
|
|
&& stdout.contains("phi { i1, i32 }")
|
|
&& !stdout.contains("@std.num.f64_to_i32_result")
|
|
&& !stdout.contains("__glagol_num_f64_to_i32_result"),
|
|
"f64-to-i32-result fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
let integral_pos = stdout
|
|
.find("f64.to_i32.integral")
|
|
.expect("integral check block is present");
|
|
let fraction_pos = stdout
|
|
.find("f64.to_i32.fraction")
|
|
.expect("fraction bit check block is present");
|
|
let fptosi_pos = stdout
|
|
.find("fptosi double")
|
|
.expect("narrowing conversion is present");
|
|
assert!(
|
|
integral_pos < fraction_pos && fraction_pos < fptosi_pos,
|
|
"f64-to-i32-result must prove integrality before fptosi\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"f64-to-i32-result fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"f64 zero narrows to i32\" ... ok\n",
|
|
"test \"negative f64 narrows to i32\" ... ok\n",
|
|
"test \"fractional f64 returns err\" ... ok\n",
|
|
"test \"above i32 range f64 returns err\" ... ok\n",
|
|
"4 test(s) passed\n",
|
|
),
|
|
"f64-to-i32-result test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"f64-to-i32-result formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_f64_to_i64_result_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"f64-to-i64-result fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("fcmp oge double")
|
|
&& stdout.contains("-9223372036854775808.0")
|
|
&& stdout.contains("fcmp olt double")
|
|
&& stdout.contains("9223372036854775808.0")
|
|
&& stdout.contains("f64.to_i64.integral")
|
|
&& stdout.contains("f64.to_i64.exponent")
|
|
&& stdout.contains("f64.to_i64.mantissa")
|
|
&& stdout.contains("f64.to_i64.fraction")
|
|
&& stdout.contains("bitcast double")
|
|
&& stdout.contains("lshr i64")
|
|
&& stdout.contains("fptosi double")
|
|
&& stdout.contains("to i64")
|
|
&& !stdout.contains("frem double")
|
|
&& stdout.contains("phi { i1, i64, i32 }")
|
|
&& !stdout.contains("@std.num.f64_to_i64_result")
|
|
&& !stdout.contains("__glagol_num_f64_to_i64_result"),
|
|
"f64-to-i64-result fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
let integral_pos = stdout
|
|
.find("f64.to_i64.integral")
|
|
.expect("integral check block is present");
|
|
let fraction_pos = stdout
|
|
.find("f64.to_i64.fraction")
|
|
.expect("fraction bit check block is present");
|
|
let fptosi_pos = stdout
|
|
.find("fptosi double")
|
|
.expect("narrowing conversion is present");
|
|
assert!(
|
|
integral_pos < fraction_pos && fraction_pos < fptosi_pos,
|
|
"f64-to-i64-result must prove integrality before fptosi\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"f64-to-i64-result fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"f64 zero narrows to i64\" ... ok\n",
|
|
"test \"negative f64 narrows to i64\" ... ok\n",
|
|
"test \"fractional f64 returns err for i64\" ... ok\n",
|
|
"test \"above i64 range f64 returns err\" ... ok\n",
|
|
"4 test(s) passed\n",
|
|
),
|
|
"f64-to-i64-result test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"f64-to-i64-result formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_result_helpers_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"result-helpers fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i1 @observe_i32_ok()")
|
|
&& stdout.contains("define i32 @unwrap_i32_ok()")
|
|
&& stdout.contains("define i1 @observe_text_ok()")
|
|
&& stdout.contains("define ptr @unwrap_text_ok()")
|
|
&& stdout.contains("__glagol_unwrap_ok_trap")
|
|
&& stdout.contains("__glagol_unwrap_err_trap")
|
|
&& !stdout.contains("@std.result.is_ok")
|
|
&& !stdout.contains("@std.result.is_err")
|
|
&& !stdout.contains("@std.result.unwrap_ok")
|
|
&& !stdout.contains("@std.result.unwrap_err"),
|
|
"result-helpers fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"result-helpers fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"std result i32 observers\" ... ok\n",
|
|
"test \"std result i32 unwraps\" ... ok\n",
|
|
"test \"std result string observers\" ... ok\n",
|
|
"test \"std result string unwraps\" ... ok\n",
|
|
"test \"legacy result helpers still work\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
"result-helpers test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "result-helpers formatter output");
|
|
}
|
|
|
|
fn assert_standard_runtime_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"standard-runtime fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare void @print_i32(i32)")
|
|
&& stdout.contains("declare void @print_string(ptr)")
|
|
&& stdout.contains("declare void @print_bool(i1)")
|
|
&& stdout.contains("declare i32 @string_len(ptr)")
|
|
&& stdout.contains("call void @print_string(ptr %")
|
|
&& stdout.contains("call void @print_bool(i1 %")
|
|
&& stdout.contains("call void @print_i32(i32 %")
|
|
&& stdout.contains("call i32 @string_len(ptr ")
|
|
&& !stdout.contains("@std."),
|
|
"standard-runtime fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"standard-runtime fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"std string equality\" ... ok\n",
|
|
"test \"std string byte length\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"standard-runtime test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"standard-runtime formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_time_sleep_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"time-sleep fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare i32 @__glagol_time_monotonic_ms()")
|
|
&& stdout.contains("declare void @__glagol_time_sleep_ms(i32)")
|
|
&& stdout.contains("call i32 @__glagol_time_monotonic_ms()")
|
|
&& stdout.contains("call void @__glagol_time_sleep_ms(i32 0)")
|
|
&& !stdout.contains("@std.time."),
|
|
"time-sleep fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"time-sleep fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"monotonic value is self equal\" ... ok\n",
|
|
"test \"sleep zero returns\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"time-sleep test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "time-sleep formatter output");
|
|
}
|
|
|
|
fn assert_owned_string_concat_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"owned-string-concat fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare ptr @__glagol_string_concat(ptr, ptr)")
|
|
&& stdout.contains("define ptr @join(ptr %left, ptr %right)")
|
|
&& stdout.contains("call ptr @__glagol_string_concat(ptr %left, ptr %right)")
|
|
&& stdout.contains("call void @print_string(ptr %")
|
|
&& stdout.contains("call void @print_i32(i32 %")
|
|
&& stdout.contains("call i32 @string_len(ptr %")
|
|
&& !stdout.contains("@std."),
|
|
"owned-string-concat fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"owned-string-concat fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"owned string concat equality\" ... ok\n",
|
|
"test \"owned string concat length\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"owned-string-concat test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"owned-string-concat formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_string_value_flow_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
|
|
assert!(
|
|
compile.status.success(),
|
|
"string-value-flow fixture compile failed\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define ptr @label()")
|
|
&& stdout.contains("define ptr @echo(ptr %value)")
|
|
&& stdout.contains("define ptr @local_label()")
|
|
&& stdout.contains("define i32 @label_len()")
|
|
&& stdout.contains("%value.addr = alloca ptr")
|
|
&& stdout.contains("call i32 @string_len(ptr %")
|
|
&& stdout.contains("call void @print_string(ptr %"),
|
|
"string-value-flow fixture LLVM shape drifted\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"string-value-flow fixture compile wrote stderr:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"string literal equality\" ... ok\n",
|
|
"test \"string parameter equality\" ... ok\n",
|
|
"test \"string call return equality\" ... ok\n",
|
|
"test \"string byte length\" ... ok\n",
|
|
"4 test(s) passed\n",
|
|
),
|
|
"string value-flow test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"string-value-flow formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_if_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected if fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @choose(i32 %value)")
|
|
&& stdout.contains("if.then")
|
|
&& stdout.contains("if.else")
|
|
&& stdout.contains("if.end")
|
|
&& stdout.contains("br i1")
|
|
&& stdout.contains(" phi i32 "),
|
|
"compiler output for if fixture lost branch shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("if chooses") && !stdout.contains("if returns bool"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for if fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"if chooses then\" ... ok\n",
|
|
"test \"if chooses else\" ... ok\n",
|
|
"test \"if returns bool\" ... ok\n",
|
|
"3 test(s) passed\n",
|
|
),
|
|
"if test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "if formatter output");
|
|
}
|
|
|
|
fn assert_struct_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected struct fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @point_sum()")
|
|
&& stdout.contains("insertvalue { i32, i32 }")
|
|
&& stdout.contains("extractvalue { i32, i32 }")
|
|
&& stdout.contains("define i32 @main()")
|
|
&& !stdout.contains("type {"),
|
|
"compiler output for struct fixture lost field-read shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("struct field access") && !stdout.contains("struct field compares"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for struct fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"struct field access\" ... ok\n",
|
|
"test \"struct field compares\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"struct test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "struct formatter output");
|
|
}
|
|
|
|
fn assert_struct_value_flow_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected struct value-flow fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define { i32, i32 } @make_point(i32 %x, i32 %y)")
|
|
&& stdout.contains("define i32 @point_x({ i32, i32 } %p)")
|
|
&& stdout.contains("define i32 @point_sum({ i32, i32 } %p)")
|
|
&& stdout.contains("alloca { i32, i32 }")
|
|
&& stdout.contains("call i32 @point_sum({ i32, i32 }")
|
|
&& !stdout.contains("type {"),
|
|
"compiler output for struct value-flow fixture lost aggregate shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("struct local value flow")
|
|
&& !stdout.contains("struct parameter value flow")
|
|
&& !stdout.contains("stored struct field access"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for struct value-flow fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"struct local value flow\" ... ok\n",
|
|
"test \"struct parameter value flow\" ... ok\n",
|
|
"test \"stored struct field access\" ... ok\n",
|
|
"3 test(s) passed\n",
|
|
),
|
|
"struct value-flow test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(
|
|
format,
|
|
&expected_format,
|
|
"struct value-flow formatter output",
|
|
);
|
|
}
|
|
|
|
fn assert_unsafe_tooling_matches_fixtures(repo: &Path, example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected unsafe fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @add_one_in_unsafe(i32 %value)")
|
|
&& stdout.contains("%0 = add i32 %value, 1")
|
|
&& stdout.contains("ret i32 %0")
|
|
&& !stdout.contains("%one.addr = alloca i32")
|
|
&& stdout.contains("define i32 @main()"),
|
|
"compiler output for unsafe fixture lost safe block shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("unsafe block returns final value")
|
|
&& !stdout.contains("unsafe block can return bool"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for unsafe fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
assert_lowering_inspector_matches_fixture(
|
|
repo,
|
|
formatter_fixture,
|
|
"--inspect-lowering=surface",
|
|
"unsafe.surface.lower",
|
|
);
|
|
assert_lowering_inspector_matches_fixture(
|
|
repo,
|
|
formatter_fixture,
|
|
"--inspect-lowering=checked",
|
|
"unsafe.checked.lower",
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"unsafe block returns final value\" ... ok\n",
|
|
"test \"unsafe block can return bool\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"unsafe test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "unsafe formatter output");
|
|
}
|
|
|
|
fn assert_vec_i32_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected vec-i32 fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("declare ptr @__glagol_vec_i32_empty()")
|
|
&& stdout.contains("declare ptr @__glagol_vec_i32_append(ptr, i32)")
|
|
&& stdout.contains("declare i32 @__glagol_vec_i32_len(ptr)")
|
|
&& stdout.contains("declare i32 @__glagol_vec_i32_index(ptr, i32)")
|
|
&& stdout.contains("declare i1 @__glagol_vec_i32_eq(ptr, ptr)")
|
|
&& stdout.contains("define ptr @empty_values()")
|
|
&& stdout.contains("define ptr @pair(i32 %base)")
|
|
&& stdout.contains("define ptr @echo(ptr %values)")
|
|
&& stdout.contains("define i32 @at(ptr %values, i32 %i)")
|
|
&& stdout.contains("call ptr @__glagol_vec_i32_append(ptr %")
|
|
&& stdout.contains("call i32 @__glagol_vec_i32_index(ptr %"),
|
|
"compiler output for vec-i32 fixture lost runtime vector shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("vec i32 empty length") && !stdout.contains("vec i32 equality"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for vec-i32 fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"vec i32 empty length\" ... ok\n",
|
|
"test \"vec i32 append length\" ... ok\n",
|
|
"test \"vec i32 index\" ... ok\n",
|
|
"test \"vec i32 append is immutable\" ... ok\n",
|
|
"test \"vec i32 equality\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
"vec-i32 test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "vec-i32 formatter output");
|
|
}
|
|
|
|
fn assert_while_tooling_matches_fixtures(example: &Path, formatter_fixture: &Path) {
|
|
let compile = run_glagol([example.as_os_str()]);
|
|
let stdout = String::from_utf8_lossy(&compile.stdout);
|
|
let stderr = String::from_utf8_lossy(&compile.stderr);
|
|
assert!(
|
|
compile.status.success(),
|
|
"compiler rejected while fixture\nstdout:\n{}\nstderr:\n{}",
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert!(
|
|
stdout.contains("define i32 @count_to(i32 %limit)")
|
|
&& stdout.contains("while.cond")
|
|
&& stdout.contains("while.body")
|
|
&& stdout.contains("while.end")
|
|
&& stdout.contains("br i1"),
|
|
"compiler output for while fixture lost loop shape\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
!stdout.contains("while counts") && !stdout.contains("while false skips"),
|
|
"compiler output should not emit top-level test names as LLVM metadata\nstdout:\n{}",
|
|
stdout
|
|
);
|
|
assert!(
|
|
stderr.is_empty(),
|
|
"compiler wrote stderr for while fixture:\n{}",
|
|
stderr
|
|
);
|
|
|
|
let run = run_glagol([OsStr::new("--run-tests"), example.as_os_str()]);
|
|
assert_success_stdout(
|
|
run,
|
|
concat!(
|
|
"test \"while counts\" ... ok\n",
|
|
"test \"while false skips\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
"while test runner output",
|
|
);
|
|
|
|
let expected_format = read(formatter_fixture);
|
|
let format = run_glagol([OsStr::new("--format"), formatter_fixture.as_os_str()]);
|
|
assert_success_stdout(format, &expected_format, "while formatter output");
|
|
}
|
|
|
|
fn assert_project_enum_imports_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/readings.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "project enum imports check");
|
|
|
|
let test_cwd = temp_root("std-layout-local-fs");
|
|
let test = run_glagol_in([OsStr::new("test"), project.as_os_str()], &test_cwd);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"local exported enum constructor\" ... ok\n",
|
|
"test \"imported enum payload constructor equality\" ... ok\n",
|
|
"test \"imported enum payload equality compares payload\" ... ok\n",
|
|
"test \"imported enum payloadless equality\" ... ok\n",
|
|
"test \"imported enum local return call flow\" ... ok\n",
|
|
"test \"imported enum parameter equality\" ... ok\n",
|
|
"test \"imported enum match missing\" ... ok\n",
|
|
"test \"imported enum match value\" ... ok\n",
|
|
"test \"imported enum match offset\" ... ok\n",
|
|
"9 test(s) passed\n",
|
|
),
|
|
"project enum imports test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_layout_local_math_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/math.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_math_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local math project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"local math i32 helpers\" ... ok\n",
|
|
"test \"local math i64 helpers\" ... ok\n",
|
|
"test \"local math f64 helpers\" ... ok\n",
|
|
"test \"explicit local math import i32 helpers\" ... ok\n",
|
|
"test \"explicit local math import i64 helpers\" ... ok\n",
|
|
"test \"explicit local math import f64 helpers\" ... ok\n",
|
|
"test \"explicit local math import all helpers\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
"std layout local math project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_math_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/math.slo").exists(),
|
|
"std import math fixture must use repo-root std/math.slo, not a local copy"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let slovo_math = read(&repo_root().join("lib/std/math.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.math ("),
|
|
"std import math fixture must use explicit `std.math` import syntax"
|
|
);
|
|
assert!(
|
|
slovo_math.starts_with("(module math (export "),
|
|
"repo-root Slovo std/math.slo must directly export imported helpers"
|
|
);
|
|
for helper in STANDARD_MATH_SOURCE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_math.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/math.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.matches(helper).count() >= 2,
|
|
"std import math main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import math project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std math import i32 helpers\" ... ok\n",
|
|
"test \"explicit std math import i64 helpers\" ... ok\n",
|
|
"test \"explicit std math import f64 helpers\" ... ok\n",
|
|
"test \"explicit std math import all helpers\" ... ok\n",
|
|
"4 test(s) passed\n",
|
|
),
|
|
"std import math project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_result_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/result.slo").exists(),
|
|
"std import result fixture must use repo-root std/result.slo, not a local copy"
|
|
);
|
|
assert!(
|
|
!project.join("src/bridge.slo").exists(),
|
|
"std import result fixture must not depend on a local bridge shim"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let slovo_result = read(&repo_root().join("lib/std/result.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.result ("),
|
|
"std import result fixture must use explicit `std.result` import syntax"
|
|
);
|
|
assert!(
|
|
slovo_result.starts_with("(module result (export "),
|
|
"repo-root Slovo std/result.slo must directly export imported helpers"
|
|
);
|
|
for helper in STANDARD_RESULT_SOURCE_SEARCH_ALPHA {
|
|
assert!(
|
|
slovo_result.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/result.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"is_ok_i32",
|
|
"is_err_i32",
|
|
"unwrap_ok_i32",
|
|
"unwrap_err_i32",
|
|
"unwrap_or_i32",
|
|
"is_ok_u32",
|
|
"is_err_u32",
|
|
"unwrap_ok_u32",
|
|
"unwrap_err_u32",
|
|
"unwrap_or_u32",
|
|
"is_err_i64",
|
|
"unwrap_err_i64",
|
|
"unwrap_or_i64",
|
|
"is_ok_u64",
|
|
"is_err_u64",
|
|
"unwrap_ok_u64",
|
|
"unwrap_err_u64",
|
|
"unwrap_or_u64",
|
|
"is_err_string",
|
|
"unwrap_err_string",
|
|
"is_err_f64",
|
|
"unwrap_err_f64",
|
|
"unwrap_or_string",
|
|
"unwrap_or_f64",
|
|
"is_ok_bool",
|
|
"is_err_bool",
|
|
"unwrap_ok_bool",
|
|
"unwrap_err_bool",
|
|
"unwrap_or_bool",
|
|
] {
|
|
assert!(
|
|
main.matches(helper).count() >= 1,
|
|
"std import result main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_RESULT_OPTION_BRIDGE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_result.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/result.slo is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import result main fixture import/use is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import result project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std result i32 wrappers\" ... ok\n",
|
|
"test \"explicit std result err wrappers\" ... ok\n",
|
|
"test \"explicit std result unwrap_or i32\" ... ok\n",
|
|
"test \"explicit std result ok_or_none i32 ok\" ... ok\n",
|
|
"test \"explicit std result ok_or_none i32 none\" ... ok\n",
|
|
"test \"explicit std result u32 wrappers\" ... ok\n",
|
|
"test \"explicit std result unwrap_or u32\" ... ok\n",
|
|
"test \"explicit std result ok_or_none u32 ok\" ... ok\n",
|
|
"test \"explicit std result ok_or_none u32 none\" ... ok\n",
|
|
"test \"explicit std result unwrap_or i64\" ... ok\n",
|
|
"test \"explicit std result ok_or_none i64 ok\" ... ok\n",
|
|
"test \"explicit std result ok_or_none i64 none\" ... ok\n",
|
|
"test \"explicit std result u64 wrappers\" ... ok\n",
|
|
"test \"explicit std result unwrap_or u64\" ... ok\n",
|
|
"test \"explicit std result ok_or_none u64 ok\" ... ok\n",
|
|
"test \"explicit std result ok_or_none u64 none\" ... ok\n",
|
|
"test \"explicit std result unwrap_or string\" ... ok\n",
|
|
"test \"explicit std result ok_or_none string ok\" ... ok\n",
|
|
"test \"explicit std result ok_or_none string none\" ... ok\n",
|
|
"test \"explicit std result unwrap_or f64\" ... ok\n",
|
|
"test \"explicit std result ok_or_none f64 ok\" ... ok\n",
|
|
"test \"explicit std result ok_or_none f64 none\" ... ok\n",
|
|
"test \"explicit std result bool helpers\" ... ok\n",
|
|
"test \"explicit std result ok_or_none bool ok\" ... ok\n",
|
|
"test \"explicit std result ok_or_none bool none\" ... ok\n",
|
|
"test \"explicit std result helpers all\" ... ok\n",
|
|
"26 test(s) passed\n",
|
|
),
|
|
"std import result project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_option_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/option.slo").exists(),
|
|
"std import option fixture must use repo-root std/option.slo, not a local copy"
|
|
);
|
|
assert!(
|
|
!project.join("src/bridge.slo").exists(),
|
|
"std import option fixture must not depend on a local bridge shim"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let slovo_option = read(&repo_root().join("lib/std/option.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.option ("),
|
|
"std import option fixture must use explicit `std.option` import syntax"
|
|
);
|
|
assert!(
|
|
slovo_option.starts_with("(module option (export "),
|
|
"repo-root Slovo std/option.slo must directly export imported helpers"
|
|
);
|
|
for helper in STANDARD_OPTION_SOURCE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_option.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/option.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.matches(helper).count() >= 2,
|
|
"std import option main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_OPTION_RESULT_BRIDGE_HELPERS_ALPHA {
|
|
assert!(
|
|
slovo_option.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/option.slo is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import option main fixture import/use is missing exp-109 bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import option project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std option i32 observation\" ... ok\n",
|
|
"test \"explicit std option i32 unwrap_some\" ... ok\n",
|
|
"test \"explicit std option i32 unwrap_or\" ... ok\n",
|
|
"test \"explicit std option i32 some_or_err ok\" ... ok\n",
|
|
"test \"explicit std option i32 some_or_err err\" ... ok\n",
|
|
"test \"explicit std option u32 observation\" ... ok\n",
|
|
"test \"explicit std option u32 unwrap_some\" ... ok\n",
|
|
"test \"explicit std option u32 unwrap_or\" ... ok\n",
|
|
"test \"explicit std option u32 some_or_err ok\" ... ok\n",
|
|
"test \"explicit std option u32 some_or_err err\" ... ok\n",
|
|
"test \"explicit std option i64 observation\" ... ok\n",
|
|
"test \"explicit std option i64 unwrap_some\" ... ok\n",
|
|
"test \"explicit std option i64 unwrap_or\" ... ok\n",
|
|
"test \"explicit std option i64 some_or_err ok\" ... ok\n",
|
|
"test \"explicit std option i64 some_or_err err\" ... ok\n",
|
|
"test \"explicit std option u64 observation\" ... ok\n",
|
|
"test \"explicit std option u64 unwrap_some\" ... ok\n",
|
|
"test \"explicit std option u64 unwrap_or\" ... ok\n",
|
|
"test \"explicit std option u64 some_or_err ok\" ... ok\n",
|
|
"test \"explicit std option u64 some_or_err err\" ... ok\n",
|
|
"test \"explicit std option f64 observation\" ... ok\n",
|
|
"test \"explicit std option f64 unwrap_some\" ... ok\n",
|
|
"test \"explicit std option f64 unwrap_or\" ... ok\n",
|
|
"test \"explicit std option f64 some_or_err ok\" ... ok\n",
|
|
"test \"explicit std option f64 some_or_err err\" ... ok\n",
|
|
"test \"explicit std option bool observation\" ... ok\n",
|
|
"test \"explicit std option bool unwrap_some\" ... ok\n",
|
|
"test \"explicit std option bool unwrap_or\" ... ok\n",
|
|
"test \"explicit std option bool some_or_err ok\" ... ok\n",
|
|
"test \"explicit std option bool some_or_err err\" ... ok\n",
|
|
"test \"explicit std option string observation\" ... ok\n",
|
|
"test \"explicit std option string unwrap_some\" ... ok\n",
|
|
"test \"explicit std option string unwrap_or\" ... ok\n",
|
|
"test \"explicit std option string some_or_err ok\" ... ok\n",
|
|
"test \"explicit std option string some_or_err err\" ... ok\n",
|
|
"test \"explicit std option helpers all\" ... ok\n",
|
|
"36 test(s) passed\n",
|
|
),
|
|
"std import option project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_time_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_tooling_matches_fixture(
|
|
project,
|
|
"time",
|
|
STANDARD_TIME_SOURCE_FACADE_ALPHA,
|
|
concat!(
|
|
"test \"explicit std time monotonic facade\" ... ok\n",
|
|
"test \"explicit std time sleep zero facade\" ... ok\n",
|
|
"test \"explicit std time facade all\" ... ok\n",
|
|
"3 test(s) passed\n",
|
|
),
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_random_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_tooling_matches_fixture(
|
|
project,
|
|
"random",
|
|
STANDARD_RANDOM_SOURCE_FACADE_ALPHA,
|
|
concat!(
|
|
"test \"explicit std random i32 non-negative facade\" ... ok\n",
|
|
"test \"explicit std random facade all\" ... ok\n",
|
|
"2 test(s) passed\n",
|
|
),
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_env_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_shape(project, "env", STANDARD_ENV_SOURCE_FACADE_ALPHA);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import env project check");
|
|
|
|
let test = run_glagol_configured([OsStr::new("test"), project.as_os_str()], |command| {
|
|
configure_standard_import_env(command);
|
|
});
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std env get missing facade\" ... ok\n",
|
|
"test \"explicit std env get result missing facade\" ... ok\n",
|
|
"test \"explicit std env has missing facade\" ... ok\n",
|
|
"test \"explicit std env get or missing facade\" ... ok\n",
|
|
"test \"explicit std env get option missing facade\" ... ok\n",
|
|
"test \"explicit std env has present facade\" ... ok\n",
|
|
"test \"explicit std env get or present facade\" ... ok\n",
|
|
"test \"explicit std env get option present facade\" ... ok\n",
|
|
"test \"explicit std env get i32 result present facade\" ... ok\n",
|
|
"test \"explicit std env get i32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit std env get u32 result present facade\" ... ok\n",
|
|
"test \"explicit std env get u32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit std env get i64 result present facade\" ... ok\n",
|
|
"test \"explicit std env get i64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit std env get u64 result present facade\" ... ok\n",
|
|
"test \"explicit std env get u64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit std env get f64 result present facade\" ... ok\n",
|
|
"test \"explicit std env get f64 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit std env get bool result present facade\" ... ok\n",
|
|
"test \"explicit std env get bool or false invalid facade\" ... ok\n",
|
|
"test \"explicit std env typed option facade\" ... ok\n",
|
|
"test \"explicit std env typed custom fallback facade\" ... ok\n",
|
|
"test \"explicit std env facade all\" ... ok\n",
|
|
"23 test(s) passed\n",
|
|
),
|
|
"std import env project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_fs_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_shape(project, "fs", STANDARD_FS_SOURCE_FACADE_ALPHA);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import fs project check");
|
|
|
|
let test_cwd = temp_root("std-import-fs");
|
|
let test = run_glagol_in([OsStr::new("test"), project.as_os_str()], &test_cwd);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std fs write text status facade\" ... ok\n",
|
|
"test \"explicit std fs read text facade\" ... ok\n",
|
|
"test \"explicit std fs write text result facade\" ... ok\n",
|
|
"test \"explicit std fs read text result facade\" ... ok\n",
|
|
"test \"explicit std fs read text via handle facade\" ... ok\n",
|
|
"test \"explicit std fs open read close handle facade\" ... ok\n",
|
|
"test \"explicit std fs closed handle read err facade\" ... ok\n",
|
|
"test \"explicit std fs invalid close err facade\" ... ok\n",
|
|
"test \"explicit std fs exists file facade\" ... ok\n",
|
|
"test \"explicit std fs exists missing facade\" ... ok\n",
|
|
"test \"explicit std fs create dir result facade\" ... ok\n",
|
|
"test \"explicit std fs is dir facade\" ... ok\n",
|
|
"test \"explicit std fs create dir ok facade\" ... ok\n",
|
|
"test \"explicit std fs remove file result facade\" ... ok\n",
|
|
"test \"explicit std fs remove file ok facade\" ... ok\n",
|
|
"test \"explicit std fs read text option missing facade\" ... ok\n",
|
|
"test \"explicit std fs read text option present facade\" ... ok\n",
|
|
"test \"explicit std fs read text or missing facade\" ... ok\n",
|
|
"test \"explicit std fs read text or present facade\" ... ok\n",
|
|
"test \"explicit std fs write text ok facade\" ... ok\n",
|
|
"test \"explicit std fs read i32 result present facade\" ... ok\n",
|
|
"test \"explicit std fs read i32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit std fs read u32 result present facade\" ... ok\n",
|
|
"test \"explicit std fs read u32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit std fs read i64 result present facade\" ... ok\n",
|
|
"test \"explicit std fs read i64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit std fs read u64 result present facade\" ... ok\n",
|
|
"test \"explicit std fs read u64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit std fs read f64 result present facade\" ... ok\n",
|
|
"test \"explicit std fs read f64 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit std fs read bool result present facade\" ... ok\n",
|
|
"test \"explicit std fs read bool or false invalid facade\" ... ok\n",
|
|
"test \"explicit std fs typed option facade\" ... ok\n",
|
|
"test \"explicit std fs typed custom fallback facade\" ... ok\n",
|
|
"test \"explicit std fs facade all\" ... ok\n",
|
|
"35 test(s) passed\n",
|
|
),
|
|
"std import fs project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_net_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_tooling_matches_fixture(
|
|
project,
|
|
"net",
|
|
STANDARD_NET_SOURCE_FACADE_ALPHA,
|
|
concat!(
|
|
"test \"explicit std net invalid connect facade\" ... ok\n",
|
|
"test \"explicit std net invalid listen facade\" ... ok\n",
|
|
"test \"explicit std net invalid bound port facade\" ... ok\n",
|
|
"test \"explicit std net invalid accept facade\" ... ok\n",
|
|
"test \"explicit std net invalid read facade\" ... ok\n",
|
|
"test \"explicit std net invalid write facade\" ... ok\n",
|
|
"test \"explicit std net invalid close facade\" ... ok\n",
|
|
"test \"explicit std net helper invalids facade\" ... ok\n",
|
|
"test \"explicit std net facade all\" ... ok\n",
|
|
"9 test(s) passed\n",
|
|
),
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_json_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_tooling_matches_fixture(
|
|
project,
|
|
"json",
|
|
STANDARD_JSON_SOURCE_FACADE_ALPHA,
|
|
concat!(
|
|
"test \"explicit std json quote escapes facade\" ... ok\n",
|
|
"test \"explicit std json scalar values facade\" ... ok\n",
|
|
"test \"explicit std json primitive scalar parse success facade\" ... ok\n",
|
|
"test \"explicit std json primitive scalar parse failure facade\" ... ok\n",
|
|
"test \"explicit std json fields facade\" ... ok\n",
|
|
"test \"explicit std json arrays objects facade\" ... ok\n",
|
|
"test \"explicit std json facade all\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_process_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_shape(
|
|
project,
|
|
"process",
|
|
STANDARD_PROCESS_SOURCE_FACADE_ALPHA,
|
|
);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import process project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std process argc facade\" ... ok\n",
|
|
"test \"explicit std process arg result oob facade\" ... ok\n",
|
|
"test \"explicit std process arg option facade\" ... ok\n",
|
|
"test \"explicit std process has arg facade\" ... ok\n",
|
|
"test \"explicit std process arg fallback missing facade\" ... ok\n",
|
|
"test \"explicit std process arg fallback present facade\" ... ok\n",
|
|
"test \"explicit std process arg i32 missing facade\" ... ok\n",
|
|
"test \"explicit std process arg i32 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit std process arg u32 missing facade\" ... ok\n",
|
|
"test \"explicit std process arg u32 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit std process arg i64 missing facade\" ... ok\n",
|
|
"test \"explicit std process arg i64 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit std process arg u64 missing facade\" ... ok\n",
|
|
"test \"explicit std process arg u64 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit std process arg f64 missing facade\" ... ok\n",
|
|
"test \"explicit std process arg f64 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit std process arg bool missing facade\" ... ok\n",
|
|
"test \"explicit std process arg bool invalid fallback facade\" ... ok\n",
|
|
"test \"explicit std process typed option facade\" ... ok\n",
|
|
"test \"explicit std process typed custom fallback facade\" ... ok\n",
|
|
"test \"explicit std process facade all\" ... ok\n",
|
|
"21 test(s) passed\n",
|
|
),
|
|
"std import process project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_string_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_core_facade_tooling_matches_fixture(
|
|
project,
|
|
"string",
|
|
STANDARD_STRING_SOURCE_FACADE_ALPHA,
|
|
concat!(
|
|
"test \"explicit std string len concat\" ... ok\n",
|
|
"test \"explicit std string byte_at_result wrapper\" ... ok\n",
|
|
"test \"explicit std string slice_result wrapper\" ... ok\n",
|
|
"test \"explicit std string boundary wrappers\" ... ok\n",
|
|
"test \"explicit std string parse result wrappers\" ... ok\n",
|
|
"test \"explicit std string parse option wrappers\" ... ok\n",
|
|
"test \"explicit std string parse integer fallbacks\" ... ok\n",
|
|
"test \"explicit std string parse float bool fallbacks\" ... ok\n",
|
|
"test \"explicit std string parse custom fallbacks\" ... ok\n",
|
|
"test \"explicit std string helpers all\" ... ok\n",
|
|
"10 test(s) passed\n",
|
|
),
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_num_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_core_facade_tooling_matches_fixture(
|
|
project,
|
|
"num",
|
|
STANDARD_NUM_SOURCE_FACADE_ALPHA,
|
|
concat!(
|
|
"test \"explicit std num widening\" ... ok\n",
|
|
"test \"explicit std num checked conversions\" ... ok\n",
|
|
"test \"explicit std num to string\" ... ok\n",
|
|
"test \"explicit std num checked fallbacks\" ... ok\n",
|
|
"test \"explicit std num helpers all\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_io_tooling_matches_fixture(project: &Path) {
|
|
assert_project_std_import_host_facade_shape(project, "io", STANDARD_IO_SOURCE_FACADE_ALPHA);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import io project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std io i64 zero facade\" ... ok\n",
|
|
"test \"explicit std io u32 zero facade\" ... ok\n",
|
|
"test \"explicit std io u64 zero facade\" ... ok\n",
|
|
"test \"explicit std io f64 zero facade\" ... ok\n",
|
|
"test \"explicit std io value facade\" ... ok\n",
|
|
"test \"explicit std io stdin result facade\" ... ok\n",
|
|
"test \"explicit std io stdin option facade\" ... ok\n",
|
|
"test \"explicit std io stdin text fallback facade\" ... ok\n",
|
|
"test \"explicit std io stdin typed result facade\" ... ok\n",
|
|
"test \"explicit std io stdin typed option facade\" ... ok\n",
|
|
"test \"explicit std io stdin typed fallback facade\" ... ok\n",
|
|
"test \"explicit std io helpers all\" ... ok\n",
|
|
"12 test(s) passed\n",
|
|
),
|
|
"std import io project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_cli_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/cli.slo").exists(),
|
|
"std import cli fixture must use repo-root std/cli.slo, not a local copy"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let slovo_cli = read(&repo_root().join("lib/std/cli.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.cli ("),
|
|
"std import cli fixture must use explicit `std.cli` import syntax"
|
|
);
|
|
assert!(
|
|
slovo_cli.contains("(import std.process (arg_result))")
|
|
&& slovo_cli
|
|
.contains("(import std.result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))")
|
|
&& slovo_cli
|
|
.contains("(import std.string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))"),
|
|
"std/cli.slo must preserve transitive standard-source imports"
|
|
);
|
|
for helper in STANDARD_CLI_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_cli.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/cli.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import cli main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import cli project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std cli arg text missing\" ... ok\n",
|
|
"test \"explicit std cli arg text option\" ... ok\n",
|
|
"test \"explicit std cli arg i32 missing\" ... ok\n",
|
|
"test \"explicit std cli arg i32 fallback missing\" ... ok\n",
|
|
"test \"explicit std cli arg u32 missing\" ... ok\n",
|
|
"test \"explicit std cli arg u32 fallback missing\" ... ok\n",
|
|
"test \"explicit std cli arg i64 missing\" ... ok\n",
|
|
"test \"explicit std cli arg i64 fallback missing\" ... ok\n",
|
|
"test \"explicit std cli arg u64 missing\" ... ok\n",
|
|
"test \"explicit std cli arg u64 fallback missing\" ... ok\n",
|
|
"test \"explicit std cli arg f64 missing\" ... ok\n",
|
|
"test \"explicit std cli arg f64 fallback missing\" ... ok\n",
|
|
"test \"explicit std cli arg bool missing\" ... ok\n",
|
|
"test \"explicit std cli arg bool fallback missing\" ... ok\n",
|
|
"test \"explicit std cli typed option\" ... ok\n",
|
|
"test \"explicit std cli typed custom fallback\" ... ok\n",
|
|
"test \"explicit std cli facade all\" ... ok\n",
|
|
"17 test(s) passed\n",
|
|
),
|
|
"std import cli project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_vec_i32_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/vec_i32.slo").exists(),
|
|
"std import vec_i32 fixture must use repo-root std/vec_i32.slo, not a local copy"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let slovo_vec_i32 = read(&repo_root().join("lib/std/vec_i32.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.vec_i32 ("),
|
|
"std import vec_i32 fixture must use explicit `std.vec_i32` import syntax"
|
|
);
|
|
assert!(
|
|
slovo_vec_i32.starts_with("(module vec_i32 (export "),
|
|
"repo-root Slovo std/vec_i32.slo must directly export imported helpers"
|
|
);
|
|
assert_std_only_contains(
|
|
&slovo_vec_i32,
|
|
&[
|
|
"std.vec.i32.empty",
|
|
"std.vec.i32.append",
|
|
"std.vec.i32.len",
|
|
"std.vec.i32.index",
|
|
"std.option",
|
|
],
|
|
"std/vec_i32.slo must use only the existing promoted std.vec.i32 runtime names",
|
|
);
|
|
assert!(
|
|
!slovo_vec_i32.contains("capacity")
|
|
&& !slovo_vec_i32.contains("reserve")
|
|
&& !slovo_vec_i32.contains("shrink")
|
|
&& !slovo_vec_i32.contains("sort")
|
|
&& !slovo_vec_i32.contains("map")
|
|
&& !slovo_vec_i32.contains("filter")
|
|
&& !slovo_vec_i32.contains("(option i64)")
|
|
&& !slovo_vec_i32.contains("(option f64)")
|
|
&& !slovo_vec_i32.contains("(option string)")
|
|
&& !slovo_vec_i32.contains("(option bool)"),
|
|
"std vec_i32 source facade must stay narrow and explicit"
|
|
);
|
|
for helper in STANDARD_VEC_I32_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
slovo_vec_i32.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/vec_i32.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import vec_i32 main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import vec_i32 project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std vec_i32 empty len facade\" ... ok\n",
|
|
"test \"explicit std vec_i32 direct at facade\" ... ok\n",
|
|
"test \"explicit std vec_i32 builder helpers\" ... ok\n",
|
|
"test \"explicit std vec_i32 constructor helpers\" ... ok\n",
|
|
"test \"explicit std vec_i32 range helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 query helpers\" ... ok\n",
|
|
"test \"explicit std vec_i32 option query helpers\" ... ok\n",
|
|
"test \"explicit std vec_i32 starts_with helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 ends_with helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 without_suffix helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 without_prefix helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 transform helpers\" ... ok\n",
|
|
"test \"explicit std vec_i32 subvec helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 insert helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 insert range helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 replace helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 replace range helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 remove helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 remove range helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 count_of helper\" ... ok\n",
|
|
"test \"explicit std vec_i32 real program helpers\" ... ok\n",
|
|
"test \"explicit std vec_i32 helpers all\" ... ok\n",
|
|
"22 test(s) passed\n",
|
|
),
|
|
"std import vec_i32 project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_vec_i64_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/vec_i64.slo").exists(),
|
|
"std import vec_i64 fixture must not use a source-root vec_i64 module copy"
|
|
);
|
|
assert!(
|
|
!project.join("std/vec_i64.slo").exists(),
|
|
"std import vec_i64 fixture must use repo-root Slovo std/vec_i64.slo, not a project-local copy"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let std_vec_i64 = read(&repo_root().join("lib/std/vec_i64.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.vec_i64 ("),
|
|
"std import vec_i64 fixture must use explicit `std.vec_i64` import syntax"
|
|
);
|
|
assert!(
|
|
std_vec_i64.starts_with("(module vec_i64 (export "),
|
|
"repo-root Slovo std/vec_i64.slo must directly export imported helpers"
|
|
);
|
|
assert_std_only_contains(
|
|
&std_vec_i64,
|
|
&[
|
|
"std.vec.i64.empty",
|
|
"std.vec.i64.append",
|
|
"std.vec.i64.len",
|
|
"std.vec.i64.index",
|
|
],
|
|
"std/vec_i64.slo must use only the existing promoted std.vec.i64 runtime names",
|
|
);
|
|
assert!(
|
|
!std_vec_i64.contains("(vec i32)")
|
|
&& !std_vec_i64.contains("(vec f64)")
|
|
&& !std_vec_i64.contains("(vec string)")
|
|
&& !std_vec_i64.contains("(vec bool)")
|
|
&& !std_vec_i64.contains("(option f64)")
|
|
&& !std_vec_i64.contains("(option string)")
|
|
&& !std_vec_i64.contains("(option bool)")
|
|
&& !std_vec_i64.contains("(result i32")
|
|
&& !std_vec_i64.contains("(result i64")
|
|
&& !std_vec_i64.contains("(result f64")
|
|
&& !std_vec_i64.contains("(result string")
|
|
&& !std_vec_i64.contains("(result bool")
|
|
&& !std_vec_i64.contains("capacity")
|
|
&& !std_vec_i64.contains("reserve")
|
|
&& !std_vec_i64.contains("shrink")
|
|
&& !std_vec_i64.contains("sort")
|
|
&& !std_vec_i64.contains("map")
|
|
&& !std_vec_i64.contains("filter"),
|
|
"std vec_i64 source facade must stay narrow and explicit"
|
|
);
|
|
for helper in STANDARD_VEC_I64_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
std_vec_i64.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/vec_i64.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import vec_i64 main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import vec_i64 project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std vec_i64 empty len facade\" ... ok\n",
|
|
"test \"explicit std vec_i64 direct at facade\" ... ok\n",
|
|
"test \"explicit std vec_i64 builder helpers\" ... ok\n",
|
|
"test \"explicit std vec_i64 query helpers\" ... ok\n",
|
|
"test \"explicit std vec_i64 option query helpers\" ... ok\n",
|
|
"test \"explicit std vec_i64 count_of helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 starts_with helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 ends_with helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 without_suffix helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 without_prefix helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 transform helpers\" ... ok\n",
|
|
"test \"explicit std vec_i64 subvec helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 insert helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 insert range helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 replace helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 replace range helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 remove helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 remove range helper\" ... ok\n",
|
|
"test \"explicit std vec_i64 real program helpers\" ... ok\n",
|
|
"test \"explicit std vec_i64 helpers all\" ... ok\n",
|
|
"20 test(s) passed\n",
|
|
),
|
|
"std import vec_i64 project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_vec_f64_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/vec_f64.slo").exists(),
|
|
"std import vec_f64 fixture must not use a source-root vec_f64 module copy"
|
|
);
|
|
assert!(
|
|
!project.join("std/vec_f64.slo").exists(),
|
|
"std import vec_f64 fixture must use repo-root Slovo std/vec_f64.slo, not a project-local copy"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let std_vec_f64 = read(&repo_root().join("lib/std/vec_f64.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.vec_f64 ("),
|
|
"std import vec_f64 fixture must use explicit `std.vec_f64` import syntax"
|
|
);
|
|
assert!(
|
|
std_vec_f64.starts_with("(module vec_f64 (export "),
|
|
"repo-root Slovo std/vec_f64.slo must directly export imported helpers"
|
|
);
|
|
assert_std_only_contains(
|
|
&std_vec_f64,
|
|
&[
|
|
"std.vec.f64.empty",
|
|
"std.vec.f64.append",
|
|
"std.vec.f64.len",
|
|
"std.vec.f64.index",
|
|
],
|
|
"std/vec_f64.slo must use only the existing promoted std.vec.f64 runtime names",
|
|
);
|
|
assert!(
|
|
!std_vec_f64.contains("(vec i32)")
|
|
&& !std_vec_f64.contains("(vec i64)")
|
|
&& !std_vec_f64.contains("(vec string)")
|
|
&& !std_vec_f64.contains("(vec bool)")
|
|
&& !std_vec_f64.contains("(option i64)")
|
|
&& !std_vec_f64.contains("(option string)")
|
|
&& !std_vec_f64.contains("(option bool)")
|
|
&& !std_vec_f64.contains("(result i32")
|
|
&& !std_vec_f64.contains("(result i64")
|
|
&& !std_vec_f64.contains("(result f64")
|
|
&& !std_vec_f64.contains("(result string")
|
|
&& !std_vec_f64.contains("(result bool")
|
|
&& !std_vec_f64.contains("capacity")
|
|
&& !std_vec_f64.contains("reserve")
|
|
&& !std_vec_f64.contains("shrink")
|
|
&& !std_vec_f64.contains("sort")
|
|
&& !std_vec_f64.contains("map")
|
|
&& !std_vec_f64.contains("filter"),
|
|
"std vec_f64 source facade must stay concrete to vec f64 plus option i32/f64 helpers"
|
|
);
|
|
for helper in STANDARD_VEC_F64_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
std_vec_f64.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/vec_f64.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import vec_f64 main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import vec_f64 project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std vec_f64 empty len facade\" ... ok\n",
|
|
"test \"explicit std vec_f64 direct at facade\" ... ok\n",
|
|
"test \"explicit std vec_f64 builder helpers\" ... ok\n",
|
|
"test \"explicit std vec_f64 query helpers\" ... ok\n",
|
|
"test \"explicit std vec_f64 option query helpers\" ... ok\n",
|
|
"test \"explicit std vec_f64 count_of helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 starts_with helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 ends_with helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 without_suffix helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 without_prefix helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 transform helpers\" ... ok\n",
|
|
"test \"explicit std vec_f64 subvec helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 insert helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 insert range helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 replace helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 replace range helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 remove helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 remove range helper\" ... ok\n",
|
|
"test \"explicit std vec_f64 real program helpers\" ... ok\n",
|
|
"test \"explicit std vec_f64 helpers all\" ... ok\n",
|
|
"20 test(s) passed\n",
|
|
),
|
|
"std import vec_f64 project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_vec_bool_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/vec_bool.slo").exists(),
|
|
"std import vec_bool fixture must not use a source-root vec_bool module copy"
|
|
);
|
|
assert!(
|
|
!project.join("std/vec_bool.slo").exists(),
|
|
"std import vec_bool fixture must use repo-root Slovo std/vec_bool.slo, not a project-local copy"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let std_vec_bool = read(&repo_root().join("lib/std/vec_bool.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.vec_bool ("),
|
|
"std import vec_bool fixture must use explicit `std.vec_bool` import syntax"
|
|
);
|
|
assert!(
|
|
std_vec_bool.starts_with("(module vec_bool (export "),
|
|
"repo-root Slovo std/vec_bool.slo must directly export imported helpers"
|
|
);
|
|
assert_std_only_contains(
|
|
&std_vec_bool,
|
|
&[
|
|
"std.vec.bool.empty",
|
|
"std.vec.bool.append",
|
|
"std.vec.bool.len",
|
|
"std.vec.bool.index",
|
|
],
|
|
"std/vec_bool.slo must use only the existing promoted std.vec.bool runtime names",
|
|
);
|
|
assert!(
|
|
!std_vec_bool.contains("(vec i32)")
|
|
&& !std_vec_bool.contains("(vec i64)")
|
|
&& !std_vec_bool.contains("(vec string)")
|
|
&& !std_vec_bool.contains("(option i64)")
|
|
&& !std_vec_bool.contains("(option f64)")
|
|
&& !std_vec_bool.contains("(option string)")
|
|
&& !std_vec_bool.contains("(result i32")
|
|
&& !std_vec_bool.contains("(result i64")
|
|
&& !std_vec_bool.contains("(result f64")
|
|
&& !std_vec_bool.contains("(result string")
|
|
&& !std_vec_bool.contains("(result bool")
|
|
&& !std_vec_bool.contains("capacity")
|
|
&& !std_vec_bool.contains("reserve")
|
|
&& !std_vec_bool.contains("shrink")
|
|
&& !std_vec_bool.contains("sort")
|
|
&& !std_vec_bool.contains("map")
|
|
&& !std_vec_bool.contains("filter"),
|
|
"std vec_bool source facade must stay concrete to vec bool plus option i32/bool helpers"
|
|
);
|
|
for helper in STANDARD_VEC_BOOL_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
std_vec_bool.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/vec_bool.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import vec_bool main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import vec_bool project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std vec_bool empty len facade\" ... ok\n",
|
|
"test \"explicit std vec_bool direct at facade\" ... ok\n",
|
|
"test \"explicit std vec_bool builder helpers\" ... ok\n",
|
|
"test \"explicit std vec_bool query helpers\" ... ok\n",
|
|
"test \"explicit std vec_bool option query helpers\" ... ok\n",
|
|
"test \"explicit std vec_bool starts_with helper\" ... ok\n",
|
|
"test \"explicit std vec_bool ends_with helper\" ... ok\n",
|
|
"test \"explicit std vec_bool without_suffix helper\" ... ok\n",
|
|
"test \"explicit std vec_bool without_prefix helper\" ... ok\n",
|
|
"test \"explicit std vec_bool transform helpers\" ... ok\n",
|
|
"test \"explicit std vec_bool subvec helper\" ... ok\n",
|
|
"test \"explicit std vec_bool insert helper\" ... ok\n",
|
|
"test \"explicit std vec_bool insert range helper\" ... ok\n",
|
|
"test \"explicit std vec_bool replace helper\" ... ok\n",
|
|
"test \"explicit std vec_bool replace range helper\" ... ok\n",
|
|
"test \"explicit std vec_bool remove helper\" ... ok\n",
|
|
"test \"explicit std vec_bool remove range helper\" ... ok\n",
|
|
"test \"explicit std vec_bool real program helpers\" ... ok\n",
|
|
"test \"explicit std vec_bool helpers all\" ... ok\n",
|
|
"19 test(s) passed\n",
|
|
),
|
|
"std import vec_bool project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_vec_string_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join("src/vec_string.slo").exists(),
|
|
"std import vec_string fixture must not use a source-root vec_string module copy"
|
|
);
|
|
assert!(
|
|
!project.join("std/vec_string.slo").exists(),
|
|
"std import vec_string fixture must use repo-root Slovo std/vec_string.slo, not a project-local copy"
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import std.vec_string ("),
|
|
"std import vec_string fixture must use explicit `std.vec_string` import syntax"
|
|
);
|
|
for helper in STANDARD_VEC_STRING_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import vec_string main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let fmt = run_glagol([
|
|
OsStr::new("fmt"),
|
|
OsStr::new("--check"),
|
|
project.as_os_str(),
|
|
]);
|
|
assert_success_stdout(fmt, "", "std import vec_string project fmt");
|
|
|
|
let slovo_vec_string = repo_root().join("lib/std/vec_string.slo");
|
|
if !slovo_vec_string.exists() {
|
|
eprintln!(
|
|
"skipping std import vec_string check/test: missing `{}`",
|
|
slovo_vec_string.display()
|
|
);
|
|
return;
|
|
}
|
|
|
|
let std_vec_string = read(&slovo_vec_string);
|
|
assert!(
|
|
std_vec_string.starts_with("(module vec_string (export "),
|
|
"repo-root Slovo std/vec_string.slo must directly export imported helpers"
|
|
);
|
|
assert_std_only_contains(
|
|
&std_vec_string,
|
|
&[
|
|
"std.vec.string.empty",
|
|
"std.vec.string.append",
|
|
"std.vec.string.len",
|
|
"std.vec.string.index",
|
|
],
|
|
"std/vec_string.slo must use only the existing promoted std.vec.string runtime names",
|
|
);
|
|
assert!(
|
|
!std_vec_string.contains("(vec i32)")
|
|
&& !std_vec_string.contains("(vec i64)")
|
|
&& !std_vec_string.contains("(vec f64)")
|
|
&& !std_vec_string.contains("(vec bool)")
|
|
&& !std_vec_string.contains("(option i64)")
|
|
&& !std_vec_string.contains("(option f64)")
|
|
&& !std_vec_string.contains("(option bool)")
|
|
&& !std_vec_string.contains("(result i32")
|
|
&& !std_vec_string.contains("(result i64")
|
|
&& !std_vec_string.contains("(result f64")
|
|
&& !std_vec_string.contains("(result string")
|
|
&& !std_vec_string.contains("(result bool")
|
|
&& !std_vec_string.contains("capacity")
|
|
&& !std_vec_string.contains("reserve")
|
|
&& !std_vec_string.contains("shrink")
|
|
&& !std_vec_string.contains("sort")
|
|
&& !std_vec_string.contains("map")
|
|
&& !std_vec_string.contains("filter")
|
|
&& !std_vec_string.contains("concat_all"),
|
|
"std vec_string source facade must stay narrow and explicit within concrete vec string plus option i32/string helpers"
|
|
);
|
|
for helper in STANDARD_VEC_STRING_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
std_vec_string.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/vec_string.slo is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import vec_string project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit std vec_string empty len facade\" ... ok\n",
|
|
"test \"explicit std vec_string direct at facade\" ... ok\n",
|
|
"test \"explicit std vec_string builder helpers\" ... ok\n",
|
|
"test \"explicit std vec_string query helpers\" ... ok\n",
|
|
"test \"explicit std vec_string option query helpers\" ... ok\n",
|
|
"test \"explicit std vec_string starts_with helper\" ... ok\n",
|
|
"test \"explicit std vec_string ends_with helper\" ... ok\n",
|
|
"test \"explicit std vec_string without_suffix helper\" ... ok\n",
|
|
"test \"explicit std vec_string without_prefix helper\" ... ok\n",
|
|
"test \"explicit std vec_string transform helpers\" ... ok\n",
|
|
"test \"explicit std vec_string subvec helper\" ... ok\n",
|
|
"test \"explicit std vec_string insert helper\" ... ok\n",
|
|
"test \"explicit std vec_string insert range helper\" ... ok\n",
|
|
"test \"explicit std vec_string replace helper\" ... ok\n",
|
|
"test \"explicit std vec_string replace range helper\" ... ok\n",
|
|
"test \"explicit std vec_string remove helper\" ... ok\n",
|
|
"test \"explicit std vec_string remove range helper\" ... ok\n",
|
|
"test \"explicit std vec_string real-program helpers\" ... ok\n",
|
|
"test \"explicit std vec_string helpers all\" ... ok\n",
|
|
"19 test(s) passed\n",
|
|
),
|
|
"std import vec_string project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_import_core_facade_tooling_matches_fixture(
|
|
project: &Path,
|
|
module: &str,
|
|
helpers: &[&str],
|
|
expected: &str,
|
|
) {
|
|
assert_project_std_import_host_facade_shape(project, module, helpers);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import core facade project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(test, expected, "std import core facade project test");
|
|
}
|
|
|
|
fn assert_project_std_import_host_facade_tooling_matches_fixture(
|
|
project: &Path,
|
|
module: &str,
|
|
helpers: &[&str],
|
|
expected: &str,
|
|
) {
|
|
assert_project_std_import_host_facade_shape(project, module, helpers);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std import host facade project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(test, expected, "std import host facade project test");
|
|
}
|
|
|
|
fn assert_project_std_import_host_facade_shape(project: &Path, module: &str, helpers: &[&str]) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert!(
|
|
!project.join(format!("src/{}.slo", module)).exists(),
|
|
"std import {} fixture must use repo-root std/{}.slo, not a local copy",
|
|
module,
|
|
module
|
|
);
|
|
|
|
let main = read(&project.join("src/main.slo"));
|
|
let slovo_source = read(&repo_root().join(format!("lib/std/{}.slo", module)));
|
|
assert!(
|
|
main.starts_with(&format!("(module main)\n\n(import std.{} (", module)),
|
|
"std import {} fixture must use explicit `std.{}` import syntax",
|
|
module,
|
|
module
|
|
);
|
|
assert!(
|
|
slovo_source.starts_with(&format!("(module {} (export ", module)),
|
|
"repo-root Slovo std/{}.slo must directly export imported helpers",
|
|
module
|
|
);
|
|
for helper in helpers {
|
|
assert!(
|
|
slovo_source.contains(&format!("(fn {} ", helper)),
|
|
"Slovo std/{}.slo is missing helper `{}`",
|
|
module,
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"std import {} main fixture import/use is missing helper `{}`",
|
|
module,
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_installed_standard_library_discovery_is_promotable(repo: &Path) {
|
|
let project_rs = read(&repo.join("compiler/src/project.rs"));
|
|
|
|
assert!(
|
|
project_rs.contains("env::current_exe()")
|
|
&& project_rs.contains("installed_standard_library_candidates")
|
|
&& project_rs.contains("../share/slovo/std"),
|
|
"standard-library discovery must include executable-relative installed `share/slovo/std`"
|
|
);
|
|
assert!(
|
|
project_rs.contains("env::split_paths(&paths)"),
|
|
"SLOVO_STD_PATH must support OS path-list discovery roots"
|
|
);
|
|
assert!(
|
|
project_rs.contains(".find(|path| path.is_file())"),
|
|
"standard-library discovery must choose the first candidate containing the requested module"
|
|
);
|
|
assert!(
|
|
project_rs.contains("set SLOVO_STD_PATH, install `share/slovo/std`"),
|
|
"missing standard-library diagnostics must mention installed stdlib discovery"
|
|
);
|
|
}
|
|
|
|
fn assert_workspace_std_import_option_tooling_matches_fixture(workspace: &Path) {
|
|
let app = workspace.join("packages/app");
|
|
let main = app.join("src/main.slo");
|
|
assert!(workspace.join("slovo.toml").is_file());
|
|
assert!(app.join("slovo.toml").is_file());
|
|
assert!(main.is_file());
|
|
assert!(
|
|
!app.join("src/option.slo").exists(),
|
|
"workspace std import option fixture must use repo-root std/option.slo, not a local copy"
|
|
);
|
|
assert!(
|
|
!app.join("src/bridge.slo").exists(),
|
|
"workspace std import option fixture must not depend on a local bridge shim"
|
|
);
|
|
|
|
let main_source = read(&main);
|
|
assert!(
|
|
main_source.starts_with("(module main)\n\n(import std.option ("),
|
|
"workspace std import option fixture must use explicit `std.option` import syntax"
|
|
);
|
|
for helper in ["is_some_i32", "is_none_i32", "unwrap_or_i32"] {
|
|
assert!(
|
|
main_source.matches(helper).count() >= 2,
|
|
"workspace std import option fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"some_or_err_i32",
|
|
"some_or_err_i64",
|
|
"some_or_err_f64",
|
|
"some_or_err_bool",
|
|
"some_or_err_string",
|
|
] {
|
|
assert!(
|
|
main_source.contains(helper),
|
|
"workspace std import option main/import is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
|
|
let check = run_glagol([OsStr::new("check"), workspace.as_os_str()]);
|
|
assert_success_stdout(check, "", "workspace std import option check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), workspace.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
"test \"workspace std option import\" ... ok\n1 test(s) passed\n",
|
|
"workspace std import option test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_math_source_helpers_alpha(project: &Path) {
|
|
let math = read(&project.join("src/math.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
let math_export_line = math.lines().next().unwrap_or_default();
|
|
|
|
assert!(
|
|
math.starts_with("(module math (export "),
|
|
"local math fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import math ("),
|
|
"local math fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!math.contains("std.") && !main.contains("std."),
|
|
"standard math source helper fixture must not use compiler-known std runtime names"
|
|
);
|
|
|
|
for helper in STANDARD_MATH_SOURCE_HELPERS_ALPHA {
|
|
assert!(
|
|
math.contains(&format!("(fn {} ", helper)),
|
|
"local math fixture is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
math_export_line.contains(helper),
|
|
"local math fixture export list is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.matches(helper).count() >= 2,
|
|
"main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn normalize_local_math_fixture_helpers(source: &str) -> String {
|
|
let helper_source = source
|
|
.split("\n(fn i32_helpers_ok")
|
|
.next()
|
|
.expect("split local math helper source");
|
|
let mut lines = helper_source.lines();
|
|
let first = lines.next().unwrap_or_default();
|
|
assert!(
|
|
first.starts_with("(module math (export "),
|
|
"local math fixture must start with an explicit export module form"
|
|
);
|
|
|
|
let mut normalized = first.to_string();
|
|
for line in lines {
|
|
normalized.push('\n');
|
|
normalized.push_str(line);
|
|
}
|
|
normalized.trim_end().to_string()
|
|
}
|
|
|
|
fn normalize_local_vec_i32_fixture_helpers(source: &str) -> String {
|
|
source
|
|
.replace(
|
|
"(import option (some_i32 none_i32))",
|
|
"(import std.option (some_i32 none_i32))",
|
|
)
|
|
.trim_end()
|
|
.to_string()
|
|
}
|
|
|
|
fn assert_math_loop_benchmark_scaffold_is_promotable(root: &Path) {
|
|
for relative in [
|
|
"slovo.toml",
|
|
"README.md",
|
|
"benchmark.json",
|
|
"src/main.slo",
|
|
"clojure/math_loop.clj",
|
|
"common-lisp/math_loop.lisp",
|
|
"c/math_loop.c",
|
|
"rust/math_loop.rs",
|
|
"python/math_loop.py",
|
|
"run.py",
|
|
] {
|
|
assert!(
|
|
root.join(relative).is_file(),
|
|
"math-loop benchmark scaffold is missing `{}`",
|
|
relative
|
|
);
|
|
}
|
|
|
|
let slovo = read(&root.join("src/main.slo"));
|
|
let readme = read(&root.join("README.md"));
|
|
let spec = read(&root.join("benchmark.json"));
|
|
let runner = read(&root.join("run.py"));
|
|
let c = read(&root.join("c/math_loop.c"));
|
|
let rust = read(&root.join("rust/math_loop.rs"));
|
|
let python = read(&root.join("python/math_loop.py"));
|
|
let clojure = read(&root.join("clojure/math_loop.clj"));
|
|
let common_lisp = read(&root.join("common-lisp/math_loop.lisp"));
|
|
|
|
assert!(
|
|
spec.contains(r#""benchmark": "math-loop""#)
|
|
&& spec.contains(r#""source_stem": "math_loop""#)
|
|
&& spec.contains(r#""expected_checksum": "5000001""#)
|
|
&& spec.contains(r#""hot_loop_count": 10000000"#)
|
|
&& spec.contains(r#""hot_expected_checksum": "50000001""#),
|
|
"math-loop benchmark metadata must keep benchmark identity and cold/hot checksums"
|
|
);
|
|
assert!(
|
|
readme.contains("not a published benchmark result")
|
|
&& readme.contains("loop count")
|
|
&& readme.contains("run.py --list"),
|
|
"math-loop benchmark README must document local-only timing boundaries"
|
|
);
|
|
assert!(
|
|
slovo.contains("(fn math_loop ((limit i32)) -> i32")
|
|
&& slovo.contains("(std.io.read_stdin_result)")
|
|
&& slovo.contains("(std.process.arg 1)")
|
|
&& slovo.contains("(std.string.parse_i32_result text)")
|
|
&& slovo.contains("(std.io.print_i32 result)"),
|
|
"Slovo math-loop benchmark must keep runtime loop-count input and checksum output"
|
|
);
|
|
assert!(
|
|
runner.contains("local-machine comparison only")
|
|
|| runner.contains("from runner import main"),
|
|
"math-loop runner must stay an explicit local timing harness wrapper"
|
|
);
|
|
for (language, source) in [
|
|
("C", c),
|
|
("Rust", rust),
|
|
("Python", python),
|
|
("Clojure", clojure),
|
|
("Common Lisp", common_lisp),
|
|
] {
|
|
assert!(
|
|
(source.contains("EXPECTED_CHECKSUM")
|
|
|| source.contains("expected-checksum")
|
|
|| source.contains("+expected-checksum+"))
|
|
&& (source.contains("LOOP_COUNT")
|
|
|| source.contains("loop-count")
|
|
|| source.contains("+loop-count+")),
|
|
"{} math-loop fixture must keep shared constants",
|
|
language
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_named_benchmark_scaffold_is_promotable(root: &Path, name: &str, source_stem: &str) {
|
|
for relative in [
|
|
"slovo.toml",
|
|
"README.md",
|
|
"benchmark.json",
|
|
"src/main.slo",
|
|
"run.py",
|
|
] {
|
|
assert!(
|
|
root.join(relative).is_file(),
|
|
"{} benchmark scaffold is missing `{}`",
|
|
name,
|
|
relative
|
|
);
|
|
}
|
|
|
|
for relative in [
|
|
format!("clojure/{}.clj", source_stem),
|
|
format!("common-lisp/{}.lisp", source_stem),
|
|
format!("c/{}.c", source_stem),
|
|
format!("rust/{}.rs", source_stem),
|
|
format!("python/{}.py", source_stem),
|
|
] {
|
|
assert!(
|
|
root.join(&relative).is_file(),
|
|
"{} benchmark scaffold is missing `{}`",
|
|
name,
|
|
relative
|
|
);
|
|
}
|
|
|
|
let spec = read(&root.join("benchmark.json"));
|
|
let slovo = read(&root.join("src/main.slo"));
|
|
let readme = read(&root.join("README.md"));
|
|
let runner = read(&root.join("run.py"));
|
|
|
|
assert!(
|
|
spec.contains(&format!(r#""benchmark": "{}""#, name))
|
|
&& spec.contains(&format!(r#""source_stem": "{}""#, source_stem))
|
|
&& spec.contains(r#""loop_count": 1000000"#)
|
|
&& spec.contains(r#""expected_checksum": "#)
|
|
&& spec.contains(r#""hot_loop_count": 10000000"#)
|
|
&& spec.contains(r#""hot_expected_checksum": "#),
|
|
"{} benchmark metadata must keep identity, source stem, cold/hot loop counts, and checksums",
|
|
name
|
|
);
|
|
assert!(
|
|
readme.contains("not a published benchmark result")
|
|
&& readme.contains("same machine")
|
|
&& readme.contains("runtime"),
|
|
"{} benchmark README must document local-only timing boundaries",
|
|
name
|
|
);
|
|
assert!(
|
|
slovo.contains("(std.io.read_stdin_result)")
|
|
&& slovo.contains("(std.process.arg ")
|
|
&& slovo.contains("(std.io.print_i32 result)")
|
|
&& runner.contains("from runner import main"),
|
|
"{} benchmark must keep runtime loop-count input and shared runner wrapper",
|
|
name
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_layout_local_option_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/option.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_option_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local option project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local option i32 observation\" ... ok\n",
|
|
"test \"explicit local option i32 unwrap_some\" ... ok\n",
|
|
"test \"explicit local option i32 unwrap_or\" ... ok\n",
|
|
"test \"explicit local option i32 some_or_err ok\" ... ok\n",
|
|
"test \"explicit local option i32 some_or_err err\" ... ok\n",
|
|
"test \"explicit local option u32 observation\" ... ok\n",
|
|
"test \"explicit local option u32 unwrap_some\" ... ok\n",
|
|
"test \"explicit local option u32 unwrap_or\" ... ok\n",
|
|
"test \"explicit local option u32 some_or_err ok\" ... ok\n",
|
|
"test \"explicit local option u32 some_or_err err\" ... ok\n",
|
|
"test \"explicit local option i64 observation\" ... ok\n",
|
|
"test \"explicit local option i64 unwrap_some\" ... ok\n",
|
|
"test \"explicit local option i64 unwrap_or\" ... ok\n",
|
|
"test \"explicit local option i64 some_or_err ok\" ... ok\n",
|
|
"test \"explicit local option i64 some_or_err err\" ... ok\n",
|
|
"test \"explicit local option u64 observation\" ... ok\n",
|
|
"test \"explicit local option u64 unwrap_some\" ... ok\n",
|
|
"test \"explicit local option u64 unwrap_or\" ... ok\n",
|
|
"test \"explicit local option u64 some_or_err ok\" ... ok\n",
|
|
"test \"explicit local option u64 some_or_err err\" ... ok\n",
|
|
"test \"explicit local option f64 observation\" ... ok\n",
|
|
"test \"explicit local option f64 unwrap_some\" ... ok\n",
|
|
"test \"explicit local option f64 unwrap_or\" ... ok\n",
|
|
"test \"explicit local option f64 some_or_err ok\" ... ok\n",
|
|
"test \"explicit local option f64 some_or_err err\" ... ok\n",
|
|
"test \"explicit local option bool observation\" ... ok\n",
|
|
"test \"explicit local option bool unwrap_some\" ... ok\n",
|
|
"test \"explicit local option bool unwrap_or\" ... ok\n",
|
|
"test \"explicit local option bool some_or_err ok\" ... ok\n",
|
|
"test \"explicit local option bool some_or_err err\" ... ok\n",
|
|
"test \"explicit local option string observation\" ... ok\n",
|
|
"test \"explicit local option string unwrap_some\" ... ok\n",
|
|
"test \"explicit local option string unwrap_or\" ... ok\n",
|
|
"test \"explicit local option string some_or_err ok\" ... ok\n",
|
|
"test \"explicit local option string some_or_err err\" ... ok\n",
|
|
"test \"explicit local option helpers all\" ... ok\n",
|
|
"36 test(s) passed\n",
|
|
),
|
|
"std layout local option project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_option_source_helpers_alpha(project: &Path) {
|
|
let option = read(&project.join("src/option.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
option.starts_with("(module option (export "),
|
|
"local option fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import option ("),
|
|
"local option fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!option.contains("std.") && !main.contains("std."),
|
|
"standard option source helper fixture must not use compiler-known std runtime names"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard option source helper fixture must not use automatic std imports"
|
|
);
|
|
assert!(
|
|
!option.contains("std.result.")
|
|
&& !main.contains("std.result.")
|
|
&& !main.contains("(import result"),
|
|
"standard option source helper fixture must bridge through raw concrete result forms, not compiler-known std.result names or a separate local result module"
|
|
);
|
|
|
|
for helper in STANDARD_OPTION_SOURCE_HELPERS_ALPHA {
|
|
assert!(
|
|
option.contains(&format!("(fn {} ", helper)),
|
|
"local option fixture is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_OPTION_RESULT_BRIDGE_HELPERS_ALPHA {
|
|
assert!(
|
|
option.contains(&format!("(fn {} ", helper)),
|
|
"local option fixture is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_num_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/num.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_num_source_fallback_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local num project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local num widening\" ... ok\n",
|
|
"test \"explicit local num checked conversions\" ... ok\n",
|
|
"test \"explicit local num to string\" ... ok\n",
|
|
"test \"explicit local num checked fallbacks\" ... ok\n",
|
|
"test \"explicit local num helpers all\" ... ok\n",
|
|
"5 test(s) passed\n",
|
|
),
|
|
"std layout local num project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_num_source_fallback_helpers_alpha(project: &Path) {
|
|
let num_source = read(&project.join("src/num.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
num_source.starts_with("(module num (export "),
|
|
"local num fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import num ("),
|
|
"local num fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard num source facade fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&num_source,
|
|
&[
|
|
"std.num.i32_to_i64",
|
|
"std.num.i32_to_f64",
|
|
"std.num.i64_to_f64",
|
|
"std.num.i64_to_i32_result",
|
|
"std.num.f64_to_i32_result",
|
|
"std.num.f64_to_i64_result",
|
|
"std.num.i32_to_string",
|
|
"std.num.u32_to_string",
|
|
"std.num.i64_to_string",
|
|
"std.num.u64_to_string",
|
|
"std.num.f64_to_string",
|
|
],
|
|
"standard num source facade fixture must use only existing std.num runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std."),
|
|
"standard num source facade main fixture must remain local and explicit"
|
|
);
|
|
assert!(
|
|
!num_source.contains("saturat")
|
|
&& !num_source.contains("round")
|
|
&& !num_source.contains("floor")
|
|
&& !num_source.contains("ceil")
|
|
&& !num_source.contains("generic")
|
|
&& !main.contains("saturat")
|
|
&& !main.contains("round")
|
|
&& !main.contains("floor")
|
|
&& !main.contains("ceil")
|
|
&& !main.contains("generic"),
|
|
"standard num source facade fixture must not claim deferred numeric conversion policies or generic abstractions"
|
|
);
|
|
for helper in STANDARD_NUM_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
num_source.contains(&format!("(fn {} ", helper)),
|
|
"local num fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_process_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/process.slo").is_file());
|
|
assert!(project.join("src/string.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_process_source_fallback_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local process project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local process argc facade\" ... ok\n",
|
|
"test \"explicit local process arg result oob facade\" ... ok\n",
|
|
"test \"explicit local process arg option facade\" ... ok\n",
|
|
"test \"explicit local process has arg facade\" ... ok\n",
|
|
"test \"explicit local process arg fallback missing facade\" ... ok\n",
|
|
"test \"explicit local process arg fallback present facade\" ... ok\n",
|
|
"test \"explicit local process arg i32 missing facade\" ... ok\n",
|
|
"test \"explicit local process arg i32 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit local process arg u32 missing facade\" ... ok\n",
|
|
"test \"explicit local process arg u32 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit local process arg i64 missing facade\" ... ok\n",
|
|
"test \"explicit local process arg i64 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit local process arg u64 missing facade\" ... ok\n",
|
|
"test \"explicit local process arg u64 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit local process arg f64 missing facade\" ... ok\n",
|
|
"test \"explicit local process arg f64 invalid fallback facade\" ... ok\n",
|
|
"test \"explicit local process arg bool missing facade\" ... ok\n",
|
|
"test \"explicit local process arg bool invalid fallback facade\" ... ok\n",
|
|
"test \"explicit local process typed option facade\" ... ok\n",
|
|
"test \"explicit local process typed custom fallback facade\" ... ok\n",
|
|
"test \"explicit local process facade all\" ... ok\n",
|
|
"21 test(s) passed\n",
|
|
),
|
|
"std layout local process project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_process_source_fallback_helpers_alpha(project: &Path) {
|
|
let process = read(&project.join("src/process.slo"));
|
|
let result = read(&project.join("src/result.slo"));
|
|
let string = read(&project.join("src/string.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
process.starts_with("(module process (export "),
|
|
"local process fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
string.starts_with("(module string (export "),
|
|
"local process string fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
result.starts_with("(module result (export "),
|
|
"local process result fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import process ("),
|
|
"local process fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard process source facade fixture must not use automatic std imports"
|
|
);
|
|
assert!(
|
|
process.contains("(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))")
|
|
&& process.contains("(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))")
|
|
&& !process.contains("std.string.")
|
|
&& !process.contains("(import std.")
|
|
&& !main.contains("std."),
|
|
"standard process source facade fixture must stay local while using the promoted result bridge and parse result calls"
|
|
);
|
|
assert_std_only_contains(
|
|
&process,
|
|
&[
|
|
"std.process.arg_result",
|
|
"std.process.argc",
|
|
"std.process.arg",
|
|
],
|
|
"standard process source facade fixture must use only existing std.process runtime names directly",
|
|
);
|
|
assert_std_only_contains(
|
|
&string,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"standard process source local string fixture must use only existing std.string runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std."),
|
|
"standard process source facade main fixture must remain local and explicit"
|
|
);
|
|
assert!(
|
|
!process.contains("spawn")
|
|
&& !process.contains("exit")
|
|
&& !process.contains("cwd")
|
|
&& !process.contains("signal")
|
|
&& !process.contains("shell")
|
|
&& !process.contains("flag"),
|
|
"standard process source facade fixture must not claim deferred process or CLI framework APIs"
|
|
);
|
|
|
|
for helper in STANDARD_PROCESS_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
process.contains(&format!("(fn {} ", helper)),
|
|
"local process fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_STRING_PARSE_RESULT_HELPERS_ALPHA {
|
|
assert!(
|
|
string.contains(&format!("(fn {} ", helper)),
|
|
"local process string fixture is missing parse helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"ok_or_none_string",
|
|
"ok_or_none_i32",
|
|
"ok_or_none_u32",
|
|
"ok_or_none_i64",
|
|
"ok_or_none_u64",
|
|
"ok_or_none_f64",
|
|
"ok_or_none_bool",
|
|
] {
|
|
assert!(
|
|
result.contains(&format!("(fn {} ", helper)),
|
|
"local process result fixture is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_cli_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/cli.slo").is_file());
|
|
assert!(project.join("src/process.slo").is_file());
|
|
assert!(project.join("src/result.slo").is_file());
|
|
assert!(project.join("src/string.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_cli_source_fallback_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local cli project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
STANDARD_CLI_LOCAL_SOURCE_FALLBACK_EXPECTED_OUTPUT,
|
|
"std layout local cli project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_cli_source_fallback_helpers_alpha(project: &Path) {
|
|
let cli = read(&project.join("src/cli.slo"));
|
|
let process = read(&project.join("src/process.slo"));
|
|
let result = read(&project.join("src/result.slo"));
|
|
let string = read(&project.join("src/string.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
cli.starts_with("(module cli (export "),
|
|
"local cli fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
process.starts_with("(module process (export "),
|
|
"local cli process fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
result.starts_with("(module result (export "),
|
|
"local cli result fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
string.starts_with("(module string (export "),
|
|
"local cli string fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import cli ("),
|
|
"local cli fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard cli source fallback fixture must not use automatic std imports"
|
|
);
|
|
assert!(
|
|
cli.contains("(import process (arg_result))")
|
|
&& cli.contains("(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))")
|
|
&& cli.contains(
|
|
"(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))"
|
|
)
|
|
&& !cli.contains("(import std.")
|
|
&& !main.contains("std."),
|
|
"standard cli source fallback fixture must stay local while using local process, result, and parse helper imports"
|
|
);
|
|
assert!(
|
|
!cli.contains("std."),
|
|
"standard cli source fallback module must stay fully local and explicit"
|
|
);
|
|
assert_std_only_contains(
|
|
&process,
|
|
&[
|
|
"std.process.arg_result",
|
|
"std.process.argc",
|
|
"std.process.arg",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"standard cli source local process fixture must use only existing std.process runtime names",
|
|
);
|
|
assert_std_only_contains(
|
|
&string,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"standard cli source local string fixture must use only existing std.string runtime names",
|
|
);
|
|
assert!(
|
|
!process.contains("spawn")
|
|
&& !process.contains("exit")
|
|
&& !process.contains("cwd")
|
|
&& !process.contains("signal")
|
|
&& !process.contains("shell")
|
|
&& !process.contains("flag"),
|
|
"standard cli source local process fixture must stay narrow and avoid deferred process APIs"
|
|
);
|
|
|
|
for helper in STANDARD_CLI_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
cli.contains(&format!("(fn {} ", helper)),
|
|
"local cli fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
assert!(
|
|
process.contains("(fn arg_result "),
|
|
"local cli process fixture is missing arg_result helper"
|
|
);
|
|
for helper in [
|
|
"ok_or_none_string",
|
|
"ok_or_none_i32",
|
|
"ok_or_none_u32",
|
|
"ok_or_none_i64",
|
|
"ok_or_none_u64",
|
|
"ok_or_none_f64",
|
|
"ok_or_none_bool",
|
|
] {
|
|
assert!(
|
|
result.contains(&format!("(fn {} ", helper)),
|
|
"local cli result fixture is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_STRING_PARSE_RESULT_HELPERS_ALPHA {
|
|
assert!(
|
|
string.contains(&format!("(fn {} ", helper)),
|
|
"local cli string fixture is missing parse helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_string_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/result.slo").is_file());
|
|
assert!(project.join("src/string.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_string_source_fallback_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local string project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local string len concat\" ... ok\n",
|
|
"test \"explicit local string byte_at_result wrapper\" ... ok\n",
|
|
"test \"explicit local string slice_result wrapper\" ... ok\n",
|
|
"test \"explicit local string boundary wrappers\" ... ok\n",
|
|
"test \"explicit local string parse result wrappers\" ... ok\n",
|
|
"test \"explicit local string parse option wrappers\" ... ok\n",
|
|
"test \"explicit local string parse integer fallbacks\" ... ok\n",
|
|
"test \"explicit local string parse float bool fallbacks\" ... ok\n",
|
|
"test \"explicit local string parse custom fallbacks\" ... ok\n",
|
|
"test \"explicit local string helpers all\" ... ok\n",
|
|
"10 test(s) passed\n",
|
|
),
|
|
"std layout local string project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_string_source_fallback_helpers_alpha(project: &Path) {
|
|
let string = read(&project.join("src/string.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
string.starts_with("(module string (export "),
|
|
"local string fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import string ("),
|
|
"local string fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard string source helper fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&string,
|
|
&[
|
|
"std.string.parse_bool_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i32_result",
|
|
"std.string.byte_at_result",
|
|
"std.string.slice_result",
|
|
"std.string.starts_with",
|
|
"std.string.ends_with",
|
|
"std.string.concat",
|
|
"std.string.len",
|
|
],
|
|
"standard string source helper fixture must use only existing std.string runtime names",
|
|
);
|
|
assert!(
|
|
!string.contains("trim")
|
|
&& !string.contains("locale")
|
|
&& !string.contains("unicode")
|
|
&& !string.contains("bytes")
|
|
&& !string.contains("case_insensitive")
|
|
&& !string.contains("host_error"),
|
|
"standard string source helper fixture must not claim deferred parsing or richer error APIs"
|
|
);
|
|
|
|
for helper in STANDARD_STRING_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
string.contains(&format!("(fn {} ", helper)),
|
|
"local string fixture is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_time_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/time.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_time_source_facade_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local time project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local time monotonic facade\" ... ok\n",
|
|
"test \"explicit local time sleep zero facade\" ... ok\n",
|
|
"test \"explicit local time facade all\" ... ok\n",
|
|
"3 test(s) passed\n",
|
|
),
|
|
"std layout local time project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_time_source_facade_alpha(project: &Path) {
|
|
let time = read(&project.join("src/time.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
time.starts_with("(module time (export "),
|
|
"local time fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import time ("),
|
|
"local time fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard time source facade fixture must not use automatic std imports"
|
|
);
|
|
|
|
let mut non_time_std = time.clone();
|
|
for allowed in ["std.time.monotonic_ms", "std.time.sleep_ms"] {
|
|
non_time_std = non_time_std.replace(allowed, "");
|
|
}
|
|
assert!(
|
|
!non_time_std.contains("std.") && !main.contains("std."),
|
|
"standard time source facade fixture must use only existing std.time runtime names"
|
|
);
|
|
assert!(
|
|
time.contains("(fn sleep_ms_zero () -> i32\n (std.time.sleep_ms 0)\n 0)"),
|
|
"standard time source facade fixture must adapt unit-return sleep_ms to source i32 return"
|
|
);
|
|
assert!(
|
|
!time.contains("std.time.now")
|
|
&& !time.contains("calendar")
|
|
&& !time.contains("timezone")
|
|
&& !time.contains("async")
|
|
&& !time.contains("cancel")
|
|
&& !time.contains("schedule"),
|
|
"standard time source facade fixture must not claim deferred time APIs or scheduling semantics"
|
|
);
|
|
|
|
for helper in STANDARD_TIME_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
time.contains(&format!("(fn {} ", helper)),
|
|
"local time fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_random_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/random.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_random_source_facade_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local random project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"local random i32 non-negative facade\" ... ok\n",
|
|
"test \"explicit local random i32 non-negative facade\" ... ok\n",
|
|
"test \"explicit local random facade all\" ... ok\n",
|
|
"3 test(s) passed\n",
|
|
),
|
|
"std layout local random project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_random_source_facade_alpha(project: &Path) {
|
|
let random = read(&project.join("src/random.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
random.starts_with("(module random (export "),
|
|
"local random fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import random ("),
|
|
"local random fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard random source facade fixture must not use automatic std imports"
|
|
);
|
|
assert!(
|
|
random.contains("(std.random.i32)"),
|
|
"standard random source facade fixture must use the promoted std.random.i32 call"
|
|
);
|
|
assert_std_only_contains(
|
|
&random,
|
|
&["std.random.i32"],
|
|
"standard random source facade fixture must use only existing std.random runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std.") && !main.contains("seed") && !main.contains("crypto"),
|
|
"standard random source facade main fixture must remain local and narrow"
|
|
);
|
|
for helper in STANDARD_RANDOM_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
random.contains(&format!("(fn {} ", helper)),
|
|
"local random fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_env_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/env.slo").is_file());
|
|
assert!(project.join("src/result.slo").is_file());
|
|
assert!(project.join("src/string.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_env_source_facade_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local env project check");
|
|
|
|
let test = run_glagol_configured([OsStr::new("test"), project.as_os_str()], |command| {
|
|
configure_standard_local_env(command);
|
|
});
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local env get missing facade\" ... ok\n",
|
|
"test \"explicit local env get result missing facade\" ... ok\n",
|
|
"test \"explicit local env has missing facade\" ... ok\n",
|
|
"test \"explicit local env get or missing facade\" ... ok\n",
|
|
"test \"explicit local env get option missing facade\" ... ok\n",
|
|
"test \"explicit local env has present facade\" ... ok\n",
|
|
"test \"explicit local env get or present facade\" ... ok\n",
|
|
"test \"explicit local env get option present facade\" ... ok\n",
|
|
"test \"explicit local env get i32 result present facade\" ... ok\n",
|
|
"test \"explicit local env get i32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit local env get u32 result present facade\" ... ok\n",
|
|
"test \"explicit local env get u32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit local env get i64 result present facade\" ... ok\n",
|
|
"test \"explicit local env get i64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit local env get u64 result present facade\" ... ok\n",
|
|
"test \"explicit local env get u64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit local env get f64 result present facade\" ... ok\n",
|
|
"test \"explicit local env get f64 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit local env get bool result present facade\" ... ok\n",
|
|
"test \"explicit local env get bool or false invalid facade\" ... ok\n",
|
|
"test \"explicit local env typed option facade\" ... ok\n",
|
|
"test \"explicit local env typed custom fallback facade\" ... ok\n",
|
|
"test \"explicit local env facade all\" ... ok\n",
|
|
"23 test(s) passed\n",
|
|
),
|
|
"std layout local env project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_env_source_facade_alpha(project: &Path) {
|
|
let env_source = read(&project.join("src/env.slo"));
|
|
let result_source = read(&project.join("src/result.slo"));
|
|
let string_source = read(&project.join("src/string.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
env_source.starts_with("(module env (export "),
|
|
"local env fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
string_source.starts_with("(module string (export "),
|
|
"local env string fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
result_source.starts_with("(module result (export "),
|
|
"local env result fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import env ("),
|
|
"local env fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard env source facade fixture must not use automatic std imports"
|
|
);
|
|
assert!(
|
|
env_source.contains("(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))")
|
|
&& env_source.contains("(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))")
|
|
&& !env_source.contains("std.string.")
|
|
&& !env_source.contains("(import std.")
|
|
&& !main.contains("std.")
|
|
&& env_source.contains("(std.env.get name)")
|
|
&& env_source.contains("(std.env.get_result name)"),
|
|
"standard env source facade fixture must stay local while using the promoted env lookup, result bridge, and parse result calls"
|
|
);
|
|
assert_std_only_contains(
|
|
&env_source,
|
|
&["std.env.get_result", "std.env.get"],
|
|
"standard env source facade fixture must use only existing std.env runtime names directly",
|
|
);
|
|
assert_std_only_contains(
|
|
&string_source,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"standard env source local string fixture must use only existing std.string runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std.")
|
|
&& main.contains(STANDARD_ENV_MISSING_NAME)
|
|
&& main.contains(STANDARD_ENV_PRESENT_NAME)
|
|
&& main.contains(STANDARD_ENV_PRESENT_VALUE),
|
|
"standard env source facade main fixture must remain local and deterministic"
|
|
);
|
|
assert!(
|
|
main.contains(STANDARD_ENV_PRESENT_I32_NAME)
|
|
&& main.contains(STANDARD_ENV_PRESENT_U32_NAME)
|
|
&& main.contains(STANDARD_ENV_PRESENT_I64_NAME)
|
|
&& main.contains(STANDARD_ENV_PRESENT_U64_NAME)
|
|
&& main.contains(STANDARD_ENV_PRESENT_F64_NAME)
|
|
&& main.contains(STANDARD_ENV_PRESENT_BOOL_NAME)
|
|
&& main.contains(STANDARD_ENV_INVALID_NAME),
|
|
"standard env source facade main fixture must cover deterministic typed env names"
|
|
);
|
|
for helper in STANDARD_ENV_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
env_source.contains(&format!("(fn {} ", helper)),
|
|
"local env fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"parse_i32_result",
|
|
"parse_u32_result",
|
|
"parse_i64_result",
|
|
"parse_u64_result",
|
|
"parse_f64_result",
|
|
"parse_bool_result",
|
|
] {
|
|
assert!(
|
|
string_source.contains(&format!("(fn {} ", helper)),
|
|
"local env string fixture is missing parse helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"ok_or_none_string",
|
|
"ok_or_none_i32",
|
|
"ok_or_none_u32",
|
|
"ok_or_none_i64",
|
|
"ok_or_none_u64",
|
|
"ok_or_none_f64",
|
|
"ok_or_none_bool",
|
|
] {
|
|
assert!(
|
|
result_source.contains(&format!("(fn {} ", helper)),
|
|
"local env result fixture is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_fs_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/fs.slo").is_file());
|
|
assert!(project.join("src/result.slo").is_file());
|
|
assert!(project.join("src/string.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_fs_source_facade_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local fs project check");
|
|
|
|
let test_cwd = temp_root("std-layout-local-fs");
|
|
let test = run_glagol_in([OsStr::new("test"), project.as_os_str()], &test_cwd);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local fs write text status facade\" ... ok\n",
|
|
"test \"explicit local fs read text facade\" ... ok\n",
|
|
"test \"explicit local fs write text result facade\" ... ok\n",
|
|
"test \"explicit local fs read text result facade\" ... ok\n",
|
|
"test \"explicit local fs read text via handle facade\" ... ok\n",
|
|
"test \"explicit local fs open read close handle facade\" ... ok\n",
|
|
"test \"explicit local fs closed handle read err facade\" ... ok\n",
|
|
"test \"explicit local fs invalid close err facade\" ... ok\n",
|
|
"test \"explicit local fs exists file facade\" ... ok\n",
|
|
"test \"explicit local fs exists missing facade\" ... ok\n",
|
|
"test \"explicit local fs create dir result facade\" ... ok\n",
|
|
"test \"explicit local fs is dir facade\" ... ok\n",
|
|
"test \"explicit local fs create dir ok facade\" ... ok\n",
|
|
"test \"explicit local fs remove file result facade\" ... ok\n",
|
|
"test \"explicit local fs remove file ok facade\" ... ok\n",
|
|
"test \"explicit local fs read text option missing facade\" ... ok\n",
|
|
"test \"explicit local fs read text option present facade\" ... ok\n",
|
|
"test \"explicit local fs read text or missing facade\" ... ok\n",
|
|
"test \"explicit local fs read text or present facade\" ... ok\n",
|
|
"test \"explicit local fs write text ok facade\" ... ok\n",
|
|
"test \"explicit local fs read i32 result present facade\" ... ok\n",
|
|
"test \"explicit local fs read i32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit local fs read u32 result present facade\" ... ok\n",
|
|
"test \"explicit local fs read u32 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit local fs read i64 result present facade\" ... ok\n",
|
|
"test \"explicit local fs read i64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit local fs read u64 result present facade\" ... ok\n",
|
|
"test \"explicit local fs read u64 or zero missing facade\" ... ok\n",
|
|
"test \"explicit local fs read f64 result present facade\" ... ok\n",
|
|
"test \"explicit local fs read f64 or zero invalid facade\" ... ok\n",
|
|
"test \"explicit local fs read bool result present facade\" ... ok\n",
|
|
"test \"explicit local fs read bool or false invalid facade\" ... ok\n",
|
|
"test \"explicit local fs typed option facade\" ... ok\n",
|
|
"test \"explicit local fs typed custom fallback facade\" ... ok\n",
|
|
"test \"explicit local fs facade all\" ... ok\n",
|
|
"35 test(s) passed\n",
|
|
),
|
|
"std layout local fs project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_fs_source_facade_alpha(project: &Path) {
|
|
let fs_source = read(&project.join("src/fs.slo"));
|
|
let result_source = read(&project.join("src/result.slo"));
|
|
let string_source = read(&project.join("src/string.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
fs_source.starts_with("(module fs (export "),
|
|
"local fs fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
string_source.starts_with("(module string (export "),
|
|
"local fs string fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
result_source.starts_with("(module result (export "),
|
|
"local fs result fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import fs ("),
|
|
"local fs fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard fs source facade fixture must not use automatic std imports"
|
|
);
|
|
assert!(
|
|
fs_source.contains("(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))")
|
|
&& fs_source.contains("(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))")
|
|
&& fs_source.contains("(std.fs.read_text path)")
|
|
&& fs_source.contains("(std.fs.read_text_result path)")
|
|
&& fs_source.contains("(std.fs.write_text path text)")
|
|
&& fs_source.contains("(std.fs.write_text_result path text)")
|
|
&& fs_source.contains("(std.fs.exists path)")
|
|
&& fs_source.contains("(std.fs.is_file path)")
|
|
&& fs_source.contains("(std.fs.is_dir path)")
|
|
&& fs_source.contains("(std.fs.remove_file_result path)")
|
|
&& fs_source.contains("(std.fs.create_dir_result path)")
|
|
&& fs_source.contains("(std.fs.open_text_read_result path)")
|
|
&& fs_source.contains("(std.fs.read_open_text_result handle)")
|
|
&& fs_source.contains("(std.fs.close_result handle)")
|
|
&& !fs_source.contains("std.string.")
|
|
&& !fs_source.contains("(import std.")
|
|
&& !main.contains("std."),
|
|
"standard fs source facade fixture must stay local while using promoted fs, result bridge, and parse result calls"
|
|
);
|
|
assert_std_only_contains(
|
|
&fs_source,
|
|
&[
|
|
"std.fs.read_text_result",
|
|
"std.fs.write_text_result",
|
|
"std.fs.read_text",
|
|
"std.fs.write_text",
|
|
"std.fs.exists",
|
|
"std.fs.is_file",
|
|
"std.fs.is_dir",
|
|
"std.fs.remove_file_result",
|
|
"std.fs.create_dir_result",
|
|
"std.fs.open_text_read_result",
|
|
"std.fs.read_open_text_result",
|
|
"std.fs.close_result",
|
|
],
|
|
"standard fs source facade fixture must use only existing std.fs runtime names directly",
|
|
);
|
|
assert_std_only_contains(
|
|
&string_source,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"standard fs source local string fixture must use only existing std.string runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std.")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha.txt\"")
|
|
&& main.contains("\"std fs source search alpha\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-missing.txt\"")
|
|
&& main.contains("\"std fs source fallback alpha\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-i32.txt\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-u32.txt\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-i64.txt\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-u64.txt\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-f64.txt\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-bool.txt\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-invalid.txt\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-dir\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-dir-helper\"")
|
|
&& main.contains("\"glagol-std-layout-local-fs-alpha-remove.txt\""),
|
|
"standard fs source facade main fixture must remain local and deterministic"
|
|
);
|
|
for helper in STANDARD_FS_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
fs_source.contains(&format!("(fn {} ", helper)),
|
|
"local fs fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"parse_i32_result",
|
|
"parse_u32_result",
|
|
"parse_i64_result",
|
|
"parse_u64_result",
|
|
"parse_f64_result",
|
|
"parse_bool_result",
|
|
] {
|
|
assert!(
|
|
string_source.contains(&format!("(fn {} ", helper)),
|
|
"local fs string fixture is missing parse helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"ok_or_none_string",
|
|
"ok_or_none_i32",
|
|
"ok_or_none_u32",
|
|
"ok_or_none_i64",
|
|
"ok_or_none_u64",
|
|
"ok_or_none_f64",
|
|
"ok_or_none_bool",
|
|
] {
|
|
assert!(
|
|
result_source.contains(&format!("(fn {} ", helper)),
|
|
"local fs result fixture is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_net_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/net.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_net_source_facade_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local net project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local net invalid connect facade\" ... ok\n",
|
|
"test \"explicit local net invalid listen facade\" ... ok\n",
|
|
"test \"explicit local net invalid bound port facade\" ... ok\n",
|
|
"test \"explicit local net invalid accept facade\" ... ok\n",
|
|
"test \"explicit local net invalid read facade\" ... ok\n",
|
|
"test \"explicit local net invalid write facade\" ... ok\n",
|
|
"test \"explicit local net invalid close facade\" ... ok\n",
|
|
"test \"explicit local net helper invalids facade\" ... ok\n",
|
|
"test \"explicit local net facade all\" ... ok\n",
|
|
"9 test(s) passed\n",
|
|
),
|
|
"std layout local net project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_net_source_facade_alpha(project: &Path) {
|
|
let net_source = read(&project.join("src/net.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
net_source.starts_with("(module net (export "),
|
|
"local net fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import net ("),
|
|
"local net fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard net source facade fixture must not use automatic std imports"
|
|
);
|
|
for runtime_name in STANDARD_NET_RUNTIME_NAMES {
|
|
assert!(
|
|
net_source.contains(runtime_name),
|
|
"standard net source facade fixture must wrap `{}`",
|
|
runtime_name
|
|
);
|
|
}
|
|
assert_std_only_contains(
|
|
&net_source,
|
|
STANDARD_NET_RUNTIME_NAMES,
|
|
"standard net source facade fixture must use only existing std.net runtime names directly",
|
|
);
|
|
assert!(
|
|
!main.contains("std.")
|
|
&& !net_source.contains("dns")
|
|
&& !net_source.contains("tls")
|
|
&& !net_source.contains("udp")
|
|
&& !net_source.contains("async")
|
|
&& !net_source.contains("http")
|
|
&& !net_source.contains("timeout")
|
|
&& !net_source.contains("non_loopback")
|
|
&& !net_source.contains("host_error"),
|
|
"standard net source facade fixture must remain local and must not claim deferred networking policies"
|
|
);
|
|
for helper in STANDARD_NET_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
net_source.contains(&format!("(fn {} ", helper)),
|
|
"local net fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_json_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/json.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_json_source_facade_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local json project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local json quote escapes facade\" ... ok\n",
|
|
"test \"explicit local json scalar values facade\" ... ok\n",
|
|
"test \"explicit local json primitive scalar parse success facade\" ... ok\n",
|
|
"test \"explicit local json primitive scalar parse failure facade\" ... ok\n",
|
|
"test \"explicit local json fields facade\" ... ok\n",
|
|
"test \"explicit local json arrays objects facade\" ... ok\n",
|
|
"test \"explicit local json facade all\" ... ok\n",
|
|
"7 test(s) passed\n",
|
|
),
|
|
"std layout local json project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_json_source_facade_alpha(project: &Path) {
|
|
let json_source = read(&project.join("src/json.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
json_source.starts_with("(module json (export "),
|
|
"local json fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import json ("),
|
|
"local json fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard json source facade fixture must not use automatic std imports"
|
|
);
|
|
for runtime_name in STANDARD_JSON_RUNTIME_NAMES {
|
|
assert!(
|
|
json_source.contains(runtime_name),
|
|
"standard json source facade fixture must wrap or compose `{}`",
|
|
runtime_name
|
|
);
|
|
}
|
|
assert_std_only_contains(
|
|
&json_source,
|
|
STANDARD_JSON_RUNTIME_NAMES,
|
|
"standard json source facade fixture must use only approved std runtime names directly",
|
|
);
|
|
assert!(
|
|
!main.contains("std."),
|
|
"standard json source facade fixture main must remain local"
|
|
);
|
|
assert_deferred_json_surface_absent(&json_source, "standard json source facade fixture");
|
|
for helper in STANDARD_JSON_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
json_source.contains(&format!("(fn {} ", helper)),
|
|
"local json fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_io_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/io.slo").is_file());
|
|
assert!(project.join("src/result.slo").is_file());
|
|
assert!(project.join("src/string.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_io_source_value_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local io project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local io i64 zero facade\" ... ok\n",
|
|
"test \"explicit local io u32 zero facade\" ... ok\n",
|
|
"test \"explicit local io u64 zero facade\" ... ok\n",
|
|
"test \"explicit local io f64 zero facade\" ... ok\n",
|
|
"test \"explicit local io value facade\" ... ok\n",
|
|
"test \"explicit local io stdin result facade\" ... ok\n",
|
|
"test \"explicit local io stdin option facade\" ... ok\n",
|
|
"test \"explicit local io stdin text fallback facade\" ... ok\n",
|
|
"test \"explicit local io stdin typed result facade\" ... ok\n",
|
|
"test \"explicit local io stdin typed option facade\" ... ok\n",
|
|
"test \"explicit local io stdin typed fallback facade\" ... ok\n",
|
|
"test \"explicit local io helpers all\" ... ok\n",
|
|
"12 test(s) passed\n",
|
|
),
|
|
"std layout local io project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_io_source_value_helpers_alpha(project: &Path) {
|
|
let io_source = read(&project.join("src/io.slo"));
|
|
let result_source = read(&project.join("src/result.slo"));
|
|
let string_source = read(&project.join("src/string.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
io_source.starts_with("(module io (export "),
|
|
"local io fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
result_source.starts_with("(module result (export "),
|
|
"local io result fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
string_source.starts_with("(module string (export "),
|
|
"local io string fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import io ("),
|
|
"local io fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard io source helper fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&io_source,
|
|
&[
|
|
"std.io.print_i32",
|
|
"std.io.print_i64",
|
|
"std.io.print_u32",
|
|
"std.io.print_u64",
|
|
"std.io.print_f64",
|
|
"std.io.print_string",
|
|
"std.io.print_bool",
|
|
"std.io.read_stdin_result",
|
|
],
|
|
"standard io source helper fixture must use only existing std.io print and stdin-result runtime names directly",
|
|
);
|
|
assert!(
|
|
io_source.contains(
|
|
"(import result (ok_or_none_string ok_or_none_i32 ok_or_none_u32 ok_or_none_i64 ok_or_none_u64 ok_or_none_f64 ok_or_none_bool))",
|
|
)
|
|
&& io_source.contains(
|
|
"(import string (parse_i32_result parse_u32_result parse_i64_result parse_u64_result parse_f64_result parse_bool_result))",
|
|
)
|
|
&& io_source.contains("(std.io.read_stdin_result)")
|
|
&& !io_source.contains("eprint")
|
|
&& !io_source.contains("read_line")
|
|
&& !io_source.contains("stream")
|
|
&& !io_source.contains("async")
|
|
&& !main.contains("std.")
|
|
&& !main.contains("eprint")
|
|
&& !main.contains("read_line")
|
|
&& !main.contains("stream")
|
|
&& !main.contains("async"),
|
|
"standard io source helper fixture must stay local while using only the released stdin-result lane and must not claim deferred io helpers",
|
|
);
|
|
|
|
assert_std_only_contains(
|
|
&string_source,
|
|
&[
|
|
"std.string.len",
|
|
"std.string.concat",
|
|
"std.string.parse_i32_result",
|
|
"std.string.parse_u32_result",
|
|
"std.string.parse_i64_result",
|
|
"std.string.parse_u64_result",
|
|
"std.string.parse_f64_result",
|
|
"std.string.parse_bool_result",
|
|
],
|
|
"local io string fixture must not introduce other compiler-known std names",
|
|
);
|
|
assert_std_only_contains(
|
|
&result_source,
|
|
&[
|
|
"std.result.is_ok",
|
|
"std.result.is_err",
|
|
"std.result.unwrap_ok",
|
|
"std.result.unwrap_err",
|
|
],
|
|
"local io result fixture must not introduce other compiler-known std names",
|
|
);
|
|
|
|
for helper in STANDARD_IO_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
io_source.contains(&format!("(fn {} ", helper)),
|
|
"local io fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_vec_i32_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/option.slo").is_file());
|
|
assert!(project.join("src/vec_i32.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_vec_i32_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local vec_i32 project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local vec_i32 empty len facade\" ... ok\n",
|
|
"test \"explicit local vec_i32 direct at facade\" ... ok\n",
|
|
"test \"explicit local vec_i32 builder helpers\" ... ok\n",
|
|
"test \"explicit local vec_i32 constructor helpers\" ... ok\n",
|
|
"test \"explicit local vec_i32 range helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 query helpers\" ... ok\n",
|
|
"test \"explicit local vec_i32 option query helpers\" ... ok\n",
|
|
"test \"explicit local vec_i32 starts_with helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 ends_with helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 without_suffix helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 without_prefix helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 transform helpers\" ... ok\n",
|
|
"test \"explicit local vec_i32 subvec helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 insert helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 insert range helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 replace helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 replace range helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 remove helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 remove range helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 count_of helper\" ... ok\n",
|
|
"test \"explicit local vec_i32 real program helpers\" ... ok\n",
|
|
"test \"explicit local vec_i32 helpers all\" ... ok\n",
|
|
"22 test(s) passed\n",
|
|
),
|
|
"std layout local vec_i32 project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_vec_i32_source_helpers_alpha(project: &Path) {
|
|
let option_source = read(&project.join("src/option.slo"));
|
|
let vec_i32_source = read(&project.join("src/vec_i32.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
option_source.starts_with("(module option (export "),
|
|
"local option helper fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
vec_i32_source.starts_with("(module vec_i32 (export "),
|
|
"local vec_i32 fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import vec_i32 ("),
|
|
"local vec_i32 fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!option_source.contains("(import std")
|
|
&& !vec_i32_source.contains("(import std")
|
|
&& !main.contains("(import std")
|
|
&& !option_source.contains("(import slovo.std")
|
|
&& !vec_i32_source.contains("(import slovo.std")
|
|
&& !main.contains("(import slovo.std"),
|
|
"standard vec_i32 source helper fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&vec_i32_source,
|
|
&[
|
|
"std.vec.i32.empty",
|
|
"std.vec.i32.append",
|
|
"std.vec.i32.len",
|
|
"std.vec.i32.index",
|
|
],
|
|
"standard vec_i32 source helper fixture must use only existing std.vec.i32 runtime names",
|
|
);
|
|
assert!(
|
|
!option_source.contains("std.") && !main.contains("std."),
|
|
"standard vec_i32 source helper main fixture must remain local and explicit"
|
|
);
|
|
assert!(
|
|
!option_source.contains("(result ")
|
|
&& !option_source.contains("(option i64)")
|
|
&& !option_source.contains("(option f64)")
|
|
&& !option_source.contains("(option string)")
|
|
&& !option_source.contains("(option bool)")
|
|
&& !vec_i32_source.contains("capacity")
|
|
&& !vec_i32_source.contains("reserve")
|
|
&& !vec_i32_source.contains("shrink")
|
|
&& !vec_i32_source.contains("sort")
|
|
&& !vec_i32_source.contains("map")
|
|
&& !vec_i32_source.contains("filter")
|
|
&& !main.contains("capacity")
|
|
&& !main.contains("reserve")
|
|
&& !main.contains("shrink")
|
|
&& !main.contains("sort")
|
|
&& !main.contains("map")
|
|
&& !main.contains("filter")
|
|
&& !vec_i32_source.contains("(vec i64)")
|
|
&& !main.contains("(vec i64)")
|
|
&& !vec_i32_source.contains("(vec f64)")
|
|
&& !main.contains("(vec f64)")
|
|
&& !vec_i32_source.contains("(vec string)")
|
|
&& !main.contains("(vec string)")
|
|
&& !vec_i32_source.contains("(vec bool)")
|
|
&& !main.contains("(vec bool)")
|
|
&& !vec_i32_source.contains("(option i64)")
|
|
&& !main.contains("(option i64)")
|
|
&& !vec_i32_source.contains("(option f64)")
|
|
&& !main.contains("(option f64)")
|
|
&& !vec_i32_source.contains("(option string)")
|
|
&& !main.contains("(option string)")
|
|
&& !vec_i32_source.contains("(option bool)")
|
|
&& !main.contains("(option bool)"),
|
|
"standard vec_i32 source helper fixture must stay concrete to i32 vec and option helpers and must not claim deferred collection APIs"
|
|
);
|
|
|
|
for helper in STANDARD_VEC_I32_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
vec_i32_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_i32 fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"repeat_loop",
|
|
"range_from_zero_loop",
|
|
"range_loop",
|
|
"concat_loop",
|
|
"take_loop",
|
|
"drop_loop",
|
|
"reverse_loop",
|
|
] {
|
|
assert!(
|
|
vec_i32_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_i32 fixture is missing private recursive helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_vec_i64_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/vec_i64.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_vec_i64_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local vec_i64 project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local vec_i64 empty len facade\" ... ok\n",
|
|
"test \"explicit local vec_i64 direct at facade\" ... ok\n",
|
|
"test \"explicit local vec_i64 builder helpers\" ... ok\n",
|
|
"test \"explicit local vec_i64 query helpers\" ... ok\n",
|
|
"test \"explicit local vec_i64 option query helpers\" ... ok\n",
|
|
"test \"explicit local vec_i64 count_of helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 starts_with helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 ends_with helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 without_suffix helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 without_prefix helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 transform helpers\" ... ok\n",
|
|
"test \"explicit local vec_i64 subvec helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 insert helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 insert range helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 replace helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 replace range helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 remove helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 remove range helper\" ... ok\n",
|
|
"test \"explicit local vec_i64 real program helpers\" ... ok\n",
|
|
"test \"explicit local vec_i64 helpers all\" ... ok\n",
|
|
"20 test(s) passed\n",
|
|
),
|
|
"std layout local vec_i64 project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_layout_local_vec_f64_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/vec_f64.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_vec_f64_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local vec_f64 project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local vec_f64 empty len facade\" ... ok\n",
|
|
"test \"explicit local vec_f64 direct at facade\" ... ok\n",
|
|
"test \"explicit local vec_f64 builder helpers\" ... ok\n",
|
|
"test \"explicit local vec_f64 query helpers\" ... ok\n",
|
|
"test \"explicit local vec_f64 option query helpers\" ... ok\n",
|
|
"test \"explicit local vec_f64 count_of helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 starts_with helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 ends_with helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 without_suffix helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 without_prefix helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 transform helpers\" ... ok\n",
|
|
"test \"explicit local vec_f64 subvec helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 insert helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 insert range helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 replace helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 replace range helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 remove helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 remove range helper\" ... ok\n",
|
|
"test \"explicit local vec_f64 real program helpers\" ... ok\n",
|
|
"test \"explicit local vec_f64 helpers all\" ... ok\n",
|
|
"20 test(s) passed\n",
|
|
),
|
|
"std layout local vec_f64 project test",
|
|
);
|
|
}
|
|
|
|
fn assert_project_std_layout_local_vec_bool_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/vec_bool.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_vec_bool_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local vec_bool project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local vec_bool empty len facade\" ... ok\n",
|
|
"test \"explicit local vec_bool direct at facade\" ... ok\n",
|
|
"test \"explicit local vec_bool builder helpers\" ... ok\n",
|
|
"test \"explicit local vec_bool query helpers\" ... ok\n",
|
|
"test \"explicit local vec_bool option query helpers\" ... ok\n",
|
|
"test \"explicit local vec_bool starts_with helper\" ... ok\n",
|
|
"test \"explicit local vec_bool ends_with helper\" ... ok\n",
|
|
"test \"explicit local vec_bool without_suffix helper\" ... ok\n",
|
|
"test \"explicit local vec_bool without_prefix helper\" ... ok\n",
|
|
"test \"explicit local vec_bool transform helpers\" ... ok\n",
|
|
"test \"explicit local vec_bool subvec helper\" ... ok\n",
|
|
"test \"explicit local vec_bool insert helper\" ... ok\n",
|
|
"test \"explicit local vec_bool insert range helper\" ... ok\n",
|
|
"test \"explicit local vec_bool replace helper\" ... ok\n",
|
|
"test \"explicit local vec_bool replace range helper\" ... ok\n",
|
|
"test \"explicit local vec_bool remove helper\" ... ok\n",
|
|
"test \"explicit local vec_bool remove range helper\" ... ok\n",
|
|
"test \"explicit local vec_bool real program helpers\" ... ok\n",
|
|
"test \"explicit local vec_bool helpers all\" ... ok\n",
|
|
"19 test(s) passed\n",
|
|
),
|
|
"std layout local vec_bool project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_vec_i64_source_helpers_alpha(project: &Path) {
|
|
let vec_i64_source = read(&project.join("src/vec_i64.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
vec_i64_source.starts_with("(module vec_i64 (export "),
|
|
"local vec_i64 fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import vec_i64 ("),
|
|
"local vec_i64 fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!vec_i64_source.contains("(import std")
|
|
&& !main.contains("(import std.")
|
|
&& !vec_i64_source.contains("(import slovo.std")
|
|
&& !main.contains("(import slovo.std"),
|
|
"standard vec_i64 source helper fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&vec_i64_source,
|
|
&[
|
|
"std.vec.i64.empty",
|
|
"std.vec.i64.append",
|
|
"std.vec.i64.len",
|
|
"std.vec.i64.index",
|
|
],
|
|
"standard vec_i64 source helper fixture must use only existing std.vec.i64 runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std."),
|
|
"standard vec_i64 source helper main fixture must remain local and explicit"
|
|
);
|
|
assert!(
|
|
!vec_i64_source.contains("(var ")
|
|
&& !main.contains("(var ")
|
|
&& !vec_i64_source.contains("(set ")
|
|
&& !main.contains("(set ")
|
|
&& !vec_i64_source.contains("capacity")
|
|
&& !vec_i64_source.contains("reserve")
|
|
&& !vec_i64_source.contains("shrink")
|
|
&& !vec_i64_source.contains("sort")
|
|
&& !vec_i64_source.contains("map")
|
|
&& !vec_i64_source.contains("filter")
|
|
&& !vec_i64_source.contains("(vec i32)")
|
|
&& !main.contains("(vec i32)")
|
|
&& !vec_i64_source.contains("(vec f64)")
|
|
&& !main.contains("(vec f64)")
|
|
&& !vec_i64_source.contains("(vec string)")
|
|
&& !main.contains("(vec string)")
|
|
&& !vec_i64_source.contains("(vec bool)")
|
|
&& !main.contains("(vec bool)")
|
|
&& !vec_i64_source.contains("(option f64)")
|
|
&& !main.contains("(option f64)")
|
|
&& !vec_i64_source.contains("(option string)")
|
|
&& !main.contains("(option string)")
|
|
&& !vec_i64_source.contains("(option bool)")
|
|
&& !main.contains("(option bool)")
|
|
&& !vec_i64_source.contains("(result i32")
|
|
&& !main.contains("(result i32")
|
|
&& !vec_i64_source.contains("(result i64")
|
|
&& !main.contains("(result i64")
|
|
&& !vec_i64_source.contains("(result f64")
|
|
&& !main.contains("(result f64")
|
|
&& !vec_i64_source.contains("(result string")
|
|
&& !main.contains("(result string")
|
|
&& !vec_i64_source.contains("(result bool")
|
|
&& !main.contains("(result bool"),
|
|
"standard vec_i64 source helper fixture must stay concrete to vec i64 plus option i32/i64 helpers and must not claim deferred collection APIs"
|
|
);
|
|
|
|
for helper in STANDARD_VEC_I64_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
vec_i64_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_i64 fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"index_of_option_loop",
|
|
"last_index_of_option_loop",
|
|
"contains_loop",
|
|
"sum_loop",
|
|
"concat_loop",
|
|
"take_loop",
|
|
"drop_loop",
|
|
"reverse_loop",
|
|
] {
|
|
assert!(
|
|
vec_i64_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_i64 fixture is missing private recursive helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_standard_vec_f64_source_helpers_alpha(project: &Path) {
|
|
let vec_f64_source = read(&project.join("src/vec_f64.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
vec_f64_source.starts_with("(module vec_f64 (export "),
|
|
"local vec_f64 fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import vec_f64 ("),
|
|
"local vec_f64 fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!vec_f64_source.contains("(import std")
|
|
&& !main.contains("(import std.")
|
|
&& !vec_f64_source.contains("(import slovo.std")
|
|
&& !main.contains("(import slovo.std"),
|
|
"standard vec_f64 source helper fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&vec_f64_source,
|
|
&[
|
|
"std.vec.f64.empty",
|
|
"std.vec.f64.append",
|
|
"std.vec.f64.len",
|
|
"std.vec.f64.index",
|
|
],
|
|
"standard vec_f64 source helper fixture must use only existing std.vec.f64 runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std."),
|
|
"standard vec_f64 source helper main fixture must remain local and explicit"
|
|
);
|
|
assert!(
|
|
!vec_f64_source.contains("(var ")
|
|
&& !main.contains("(var ")
|
|
&& !vec_f64_source.contains("(set ")
|
|
&& !main.contains("(set ")
|
|
&& !vec_f64_source.contains("capacity")
|
|
&& !vec_f64_source.contains("reserve")
|
|
&& !vec_f64_source.contains("shrink")
|
|
&& !vec_f64_source.contains("sort")
|
|
&& !vec_f64_source.contains("map")
|
|
&& !vec_f64_source.contains("filter")
|
|
&& !vec_f64_source.contains("(vec i32)")
|
|
&& !main.contains("(vec i32)")
|
|
&& !vec_f64_source.contains("(vec i64)")
|
|
&& !main.contains("(vec i64)")
|
|
&& !vec_f64_source.contains("(vec string)")
|
|
&& !main.contains("(vec string)")
|
|
&& !vec_f64_source.contains("(vec bool)")
|
|
&& !main.contains("(vec bool)")
|
|
&& !vec_f64_source.contains("(option i64)")
|
|
&& !main.contains("(option i64)")
|
|
&& !vec_f64_source.contains("(option string)")
|
|
&& !main.contains("(option string)")
|
|
&& !vec_f64_source.contains("(option bool)")
|
|
&& !main.contains("(option bool)")
|
|
&& !vec_f64_source.contains("(result i32")
|
|
&& !main.contains("(result i32")
|
|
&& !vec_f64_source.contains("(result i64")
|
|
&& !main.contains("(result i64")
|
|
&& !vec_f64_source.contains("(result f64")
|
|
&& !main.contains("(result f64")
|
|
&& !vec_f64_source.contains("(result string")
|
|
&& !main.contains("(result string")
|
|
&& !vec_f64_source.contains("(result bool")
|
|
&& !main.contains("(result bool"),
|
|
"standard vec_f64 source helper fixture must stay concrete to vec f64 plus option i32/f64 helpers and must not claim deferred generic or mutation-heavy collection APIs"
|
|
);
|
|
|
|
for helper in STANDARD_VEC_F64_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
vec_f64_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_f64 fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"index_of_option_loop",
|
|
"last_index_of_option_loop",
|
|
"contains_loop",
|
|
"sum_loop",
|
|
"concat_loop",
|
|
"take_loop",
|
|
"drop_loop",
|
|
"reverse_loop",
|
|
] {
|
|
assert!(
|
|
vec_f64_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_f64 fixture is missing private recursive helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_standard_vec_bool_source_helpers_alpha(project: &Path) {
|
|
let vec_bool_source = read(&project.join("src/vec_bool.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
vec_bool_source.starts_with("(module vec_bool (export "),
|
|
"local vec_bool fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import vec_bool ("),
|
|
"local vec_bool fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!vec_bool_source.contains("(import std")
|
|
&& !main.contains("(import std.")
|
|
&& !vec_bool_source.contains("(import slovo.std")
|
|
&& !main.contains("(import slovo.std"),
|
|
"standard vec_bool source helper fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&vec_bool_source,
|
|
&[
|
|
"std.vec.bool.empty",
|
|
"std.vec.bool.append",
|
|
"std.vec.bool.len",
|
|
"std.vec.bool.index",
|
|
],
|
|
"standard vec_bool source helper fixture must use only existing std.vec.bool runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std."),
|
|
"standard vec_bool source helper main fixture must remain local and explicit"
|
|
);
|
|
assert!(
|
|
!vec_bool_source.contains("(var ")
|
|
&& !main.contains("(var ")
|
|
&& !vec_bool_source.contains("(set ")
|
|
&& !main.contains("(set ")
|
|
&& !vec_bool_source.contains("capacity")
|
|
&& !vec_bool_source.contains("reserve")
|
|
&& !vec_bool_source.contains("shrink")
|
|
&& !vec_bool_source.contains("sort")
|
|
&& !vec_bool_source.contains("map")
|
|
&& !vec_bool_source.contains("filter")
|
|
&& !vec_bool_source.contains("(vec i32)")
|
|
&& !main.contains("(vec i32)")
|
|
&& !vec_bool_source.contains("(vec i64)")
|
|
&& !main.contains("(vec i64)")
|
|
&& !vec_bool_source.contains("(vec f64)")
|
|
&& !main.contains("(vec f64)")
|
|
&& !vec_bool_source.contains("(vec string)")
|
|
&& !main.contains("(vec string)")
|
|
&& !vec_bool_source.contains("(option i64)")
|
|
&& !main.contains("(option i64)")
|
|
&& !vec_bool_source.contains("(option f64)")
|
|
&& !main.contains("(option f64)")
|
|
&& !vec_bool_source.contains("(option string)")
|
|
&& !main.contains("(option string)")
|
|
&& !vec_bool_source.contains("(result i32")
|
|
&& !main.contains("(result i32")
|
|
&& !vec_bool_source.contains("(result i64")
|
|
&& !main.contains("(result i64")
|
|
&& !vec_bool_source.contains("(result f64")
|
|
&& !main.contains("(result f64")
|
|
&& !vec_bool_source.contains("(result string")
|
|
&& !main.contains("(result string")
|
|
&& !vec_bool_source.contains("(result bool")
|
|
&& !main.contains("(result bool"),
|
|
"standard vec_bool source helper fixture must stay concrete to vec bool plus option i32/bool helpers and must not claim deferred generic or mutation-heavy collection APIs"
|
|
);
|
|
|
|
for helper in STANDARD_VEC_BOOL_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
vec_bool_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_bool fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"index_of_option_loop",
|
|
"last_index_of_option_loop",
|
|
"contains_loop",
|
|
"count_of_loop",
|
|
"concat_loop",
|
|
"take_loop",
|
|
"drop_loop",
|
|
"reverse_loop",
|
|
] {
|
|
assert!(
|
|
vec_bool_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_bool fixture is missing private recursive helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_vec_string_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/vec_string.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_vec_string_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local vec_string project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local vec_string empty len facade\" ... ok\n",
|
|
"test \"explicit local vec_string direct at facade\" ... ok\n",
|
|
"test \"explicit local vec_string builder helpers\" ... ok\n",
|
|
"test \"explicit local vec_string query helpers\" ... ok\n",
|
|
"test \"explicit local vec_string option query helpers\" ... ok\n",
|
|
"test \"explicit local vec_string starts_with helper\" ... ok\n",
|
|
"test \"explicit local vec_string ends_with helper\" ... ok\n",
|
|
"test \"explicit local vec_string without_suffix helper\" ... ok\n",
|
|
"test \"explicit local vec_string without_prefix helper\" ... ok\n",
|
|
"test \"explicit local vec_string transform helpers\" ... ok\n",
|
|
"test \"explicit local vec_string subvec helper\" ... ok\n",
|
|
"test \"explicit local vec_string insert helper\" ... ok\n",
|
|
"test \"explicit local vec_string insert range helper\" ... ok\n",
|
|
"test \"explicit local vec_string replace helper\" ... ok\n",
|
|
"test \"explicit local vec_string replace range helper\" ... ok\n",
|
|
"test \"explicit local vec_string remove helper\" ... ok\n",
|
|
"test \"explicit local vec_string remove range helper\" ... ok\n",
|
|
"test \"explicit local vec_string real-program helpers\" ... ok\n",
|
|
"test \"explicit local vec_string helpers all\" ... ok\n",
|
|
"19 test(s) passed\n",
|
|
),
|
|
"std layout local vec_string project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_vec_string_source_helpers_alpha(project: &Path) {
|
|
let vec_string_source = read(&project.join("src/vec_string.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
vec_string_source.starts_with("(module vec_string (export "),
|
|
"local vec_string fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import vec_string ("),
|
|
"local vec_string fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!vec_string_source.contains("(import std")
|
|
&& !main.contains("(import std.")
|
|
&& !vec_string_source.contains("(import slovo.std")
|
|
&& !main.contains("(import slovo.std"),
|
|
"standard vec_string source helper fixture must not use automatic std imports"
|
|
);
|
|
assert_std_only_contains(
|
|
&vec_string_source,
|
|
&[
|
|
"std.vec.string.empty",
|
|
"std.vec.string.append",
|
|
"std.vec.string.len",
|
|
"std.vec.string.index",
|
|
],
|
|
"standard vec_string source helper fixture must use only existing std.vec.string runtime names",
|
|
);
|
|
assert!(
|
|
!main.contains("std."),
|
|
"standard vec_string source helper main fixture must remain local and explicit"
|
|
);
|
|
assert!(
|
|
!vec_string_source.contains("(var ")
|
|
&& !main.contains("(var ")
|
|
&& !vec_string_source.contains("(set ")
|
|
&& !main.contains("(set ")
|
|
&& !vec_string_source.contains("capacity")
|
|
&& !vec_string_source.contains("reserve")
|
|
&& !vec_string_source.contains("shrink")
|
|
&& !vec_string_source.contains("sort")
|
|
&& !vec_string_source.contains("map")
|
|
&& !vec_string_source.contains("filter")
|
|
&& !vec_string_source.contains("concat_all")
|
|
&& !vec_string_source.contains("(vec i32)")
|
|
&& !main.contains("(vec i32)")
|
|
&& !vec_string_source.contains("(vec i64)")
|
|
&& !main.contains("(vec i64)")
|
|
&& !vec_string_source.contains("(vec f64)")
|
|
&& !main.contains("(vec f64)")
|
|
&& !vec_string_source.contains("(vec bool)")
|
|
&& !main.contains("(vec bool)")
|
|
&& !vec_string_source.contains("(option i64)")
|
|
&& !main.contains("(option i64)")
|
|
&& !vec_string_source.contains("(option f64)")
|
|
&& !main.contains("(option f64)")
|
|
&& !vec_string_source.contains("(option bool)")
|
|
&& !main.contains("(option bool)")
|
|
&& !vec_string_source.contains("(result i32")
|
|
&& !main.contains("(result i32")
|
|
&& !vec_string_source.contains("(result i64")
|
|
&& !main.contains("(result i64")
|
|
&& !vec_string_source.contains("(result f64")
|
|
&& !main.contains("(result f64")
|
|
&& !vec_string_source.contains("(result string")
|
|
&& !main.contains("(result string")
|
|
&& !vec_string_source.contains("(result bool")
|
|
&& !main.contains("(result bool"),
|
|
"standard vec_string source helper fixture must stay concrete to vec string plus option i32/string helpers and must not claim deferred collection APIs"
|
|
);
|
|
|
|
for helper in STANDARD_VEC_STRING_SOURCE_FACADE_ALPHA {
|
|
assert!(
|
|
vec_string_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_string fixture is missing facade `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing facade `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in [
|
|
"index_of_option_loop",
|
|
"last_index_of_option_loop",
|
|
"contains_loop",
|
|
"count_of_loop",
|
|
"concat_loop",
|
|
"take_loop",
|
|
"drop_loop",
|
|
"reverse_loop",
|
|
] {
|
|
assert!(
|
|
vec_string_source.contains(&format!("(fn {} ", helper)),
|
|
"local vec_string fixture is missing private recursive helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_project_std_layout_local_result_tooling_matches_fixture(project: &Path) {
|
|
assert!(project.join("slovo.toml").is_file());
|
|
assert!(project.join("src/result.slo").is_file());
|
|
assert!(project.join("src/main.slo").is_file());
|
|
assert_standard_result_source_helpers_alpha(project);
|
|
|
|
let check = run_glagol([OsStr::new("check"), project.as_os_str()]);
|
|
assert_success_stdout(check, "", "std layout local result project check");
|
|
|
|
let test = run_glagol([OsStr::new("test"), project.as_os_str()]);
|
|
assert_success_stdout(
|
|
test,
|
|
concat!(
|
|
"test \"explicit local result i32 wrappers\" ... ok\n",
|
|
"test \"explicit local result err wrappers\" ... ok\n",
|
|
"test \"explicit local result unwrap_or i32\" ... ok\n",
|
|
"test \"explicit local result ok_or_none i32 ok\" ... ok\n",
|
|
"test \"explicit local result ok_or_none i32 none\" ... ok\n",
|
|
"test \"explicit local result u32 wrappers\" ... ok\n",
|
|
"test \"explicit local result unwrap_or u32\" ... ok\n",
|
|
"test \"explicit local result ok_or_none u32 ok\" ... ok\n",
|
|
"test \"explicit local result ok_or_none u32 none\" ... ok\n",
|
|
"test \"explicit local result unwrap_or i64\" ... ok\n",
|
|
"test \"explicit local result ok_or_none i64 ok\" ... ok\n",
|
|
"test \"explicit local result ok_or_none i64 none\" ... ok\n",
|
|
"test \"explicit local result u64 wrappers\" ... ok\n",
|
|
"test \"explicit local result unwrap_or u64\" ... ok\n",
|
|
"test \"explicit local result ok_or_none u64 ok\" ... ok\n",
|
|
"test \"explicit local result ok_or_none u64 none\" ... ok\n",
|
|
"test \"explicit local result unwrap_or string\" ... ok\n",
|
|
"test \"explicit local result ok_or_none string ok\" ... ok\n",
|
|
"test \"explicit local result ok_or_none string none\" ... ok\n",
|
|
"test \"explicit local result unwrap_or f64\" ... ok\n",
|
|
"test \"explicit local result ok_or_none f64 ok\" ... ok\n",
|
|
"test \"explicit local result ok_or_none f64 none\" ... ok\n",
|
|
"test \"explicit local result bool helpers\" ... ok\n",
|
|
"test \"explicit local result ok_or_none bool ok\" ... ok\n",
|
|
"test \"explicit local result ok_or_none bool none\" ... ok\n",
|
|
"test \"explicit local result helpers all\" ... ok\n",
|
|
"26 test(s) passed\n",
|
|
),
|
|
"std layout local result project test",
|
|
);
|
|
}
|
|
|
|
fn assert_standard_result_source_helpers_alpha(project: &Path) {
|
|
let result = read(&project.join("src/result.slo"));
|
|
let main = read(&project.join("src/main.slo"));
|
|
|
|
assert!(
|
|
result.starts_with("(module result (export "),
|
|
"local result fixture must stay an explicitly exported local module"
|
|
);
|
|
assert!(
|
|
main.starts_with("(module main)\n\n(import result ("),
|
|
"local result fixture must stay an explicit local import"
|
|
);
|
|
assert!(
|
|
!main.contains("(import std") && !main.contains("(import slovo.std"),
|
|
"standard result source helper fixture must not use automatic std imports"
|
|
);
|
|
assert!(
|
|
!result.contains("std.result.unwrap_or")
|
|
&& !result.contains("std.result.map")
|
|
&& !result.contains("std.result.and_then")
|
|
&& !main.contains("std.result.unwrap_or")
|
|
&& !main.contains("std.result.map")
|
|
&& !main.contains("std.result.and_then"),
|
|
"standard result source helper fixture must keep deferred result helpers out"
|
|
);
|
|
|
|
let mut non_result_std = result.clone();
|
|
for allowed in [
|
|
"std.result.is_ok",
|
|
"std.result.is_err",
|
|
"std.result.unwrap_ok",
|
|
"std.result.unwrap_err",
|
|
] {
|
|
non_result_std = non_result_std.replace(allowed, "");
|
|
}
|
|
assert!(
|
|
!non_result_std.contains("std."),
|
|
"standard result source helper definitions must use only existing std.result names"
|
|
);
|
|
assert!(
|
|
!result.contains("std.option.")
|
|
&& !main.contains("std.option.")
|
|
&& !main.contains("(import option"),
|
|
"standard result source helper fixture must bridge through raw concrete option forms, not compiler-known std.option names or a separate local option module"
|
|
);
|
|
|
|
for helper in STANDARD_RESULT_SOURCE_HELPERS_ALPHA {
|
|
assert!(
|
|
result.contains(&format!("(fn {} ", helper)),
|
|
"local result fixture is missing helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
for helper in STANDARD_RESULT_OPTION_BRIDGE_HELPERS_ALPHA {
|
|
assert!(
|
|
result.contains(&format!("(fn {} ", helper)),
|
|
"local result fixture is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
assert!(
|
|
main.contains(helper),
|
|
"main fixture import/use is missing bridge helper `{}`",
|
|
helper
|
|
);
|
|
}
|
|
}
|
|
|
|
fn assert_success_stdout(output: Output, expected: &str, context: &str) {
|
|
let stdout = String::from_utf8_lossy(&output.stdout);
|
|
let stderr = String::from_utf8_lossy(&output.stderr);
|
|
|
|
assert!(
|
|
output.status.success(),
|
|
"{} failed\nstdout:\n{}\nstderr:\n{}",
|
|
context,
|
|
stdout,
|
|
stderr
|
|
);
|
|
assert_eq!(stdout, expected, "{} stdout drifted", context);
|
|
assert!(stderr.is_empty(), "{} wrote stderr:\n{}", context, stderr);
|
|
}
|
|
|
|
fn assert_diagnostic_snapshots_are_promotable(repo: &Path) {
|
|
assert_file_name_inventory(
|
|
&repo.join("tests"),
|
|
&["diag"],
|
|
DIAGNOSTIC_SNAPSHOTS,
|
|
"promotion gate expects every diagnostic snapshot to be explicitly inventoried",
|
|
);
|
|
|
|
for snapshot in DIAGNOSTIC_SNAPSHOTS {
|
|
let path = repo.join("tests").join(snapshot);
|
|
let content = read(&path);
|
|
|
|
assert!(
|
|
content.starts_with("(diagnostic\n"),
|
|
"`{}` must use the Slovo v1 diagnostic root",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
content.contains(" (schema slovo.diagnostic)\n"),
|
|
"`{}` is missing Slovo diagnostic schema marker",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
content.contains(" (version 1)\n"),
|
|
"`{}` is missing Slovo diagnostic schema version",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
content.contains("(severity error)"),
|
|
"`{}` is missing machine severity",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
content.contains(" (code "),
|
|
"`{}` is missing a machine diagnostic code",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
content.contains(" (file \"<fixture>\")"),
|
|
"`{}` must normalize fixture paths",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
content.contains(" (span\n") && content.contains(" (bytes "),
|
|
"`{}` is missing byte span",
|
|
path.display()
|
|
);
|
|
assert!(
|
|
content.contains(" (range "),
|
|
"`{}` is missing line/column range",
|
|
path.display()
|
|
);
|
|
|
|
if *snapshot == "test-duplicate-name.diag" {
|
|
assert!(
|
|
content.contains(" (related\n")
|
|
&& content.contains(" (message \"original test name\")")
|
|
&& content.contains(" (bytes "),
|
|
"`{}` is missing duplicate-name related span",
|
|
path.display()
|
|
);
|
|
}
|
|
}
|
|
}
|
|
|
|
fn assert_file_name_inventory(dir: &Path, extensions: &[&str], expected: &[&str], context: &str) {
|
|
let mut actual = read_dir_file_names_with_extensions(dir, extensions);
|
|
actual.sort();
|
|
|
|
let mut expected = expected
|
|
.iter()
|
|
.map(|name| (*name).to_string())
|
|
.collect::<Vec<_>>();
|
|
expected.sort();
|
|
|
|
assert_eq!(actual, expected, "{}", context);
|
|
}
|
|
|
|
fn required_llvm_shapes(expected: &str) -> Vec<&str> {
|
|
expected
|
|
.lines()
|
|
.map(str::trim)
|
|
.filter(|line| !line.is_empty())
|
|
.filter(|line| !line.starts_with(';'))
|
|
.collect()
|
|
}
|
|
|
|
fn strip_leading_comments_and_blank_lines(source: &str) -> String {
|
|
source
|
|
.lines()
|
|
.skip_while(|line| line.trim().is_empty() || line.trim_start().starts_with(';'))
|
|
.collect::<Vec<_>>()
|
|
.join("\n")
|
|
+ "\n"
|
|
}
|
|
|
|
fn strip_comments(source: &str) -> String {
|
|
source
|
|
.lines()
|
|
.map(|line| line.split_once(';').map_or(line, |(code, _)| code))
|
|
.collect::<Vec<_>>()
|
|
.join("\n")
|
|
}
|
|
|
|
fn contains_word(source: &str, word: &str) -> bool {
|
|
source
|
|
.split(|ch: char| !ch.is_ascii_alphanumeric() && ch != '_')
|
|
.any(|token| token == word)
|
|
}
|
|
|
|
fn read(path: &Path) -> String {
|
|
fs::read_to_string(path).unwrap_or_else(|err| panic!("read `{}`: {}", path.display(), err))
|
|
}
|
|
|
|
fn read_dir_files(path: &Path) -> Vec<PathBuf> {
|
|
fs::read_dir(path)
|
|
.unwrap_or_else(|err| panic!("read dir `{}`: {}", path.display(), err))
|
|
.filter_map(|entry| {
|
|
let entry = entry.unwrap_or_else(|err| panic!("read dir entry: {}", err));
|
|
let path = entry.path();
|
|
path.is_file().then_some(path)
|
|
})
|
|
.collect()
|
|
}
|
|
|
|
fn read_dir_file_names_with_extensions(path: &Path, extensions: &[&str]) -> Vec<String> {
|
|
fs::read_dir(path)
|
|
.unwrap_or_else(|err| panic!("read dir `{}`: {}", path.display(), err))
|
|
.filter_map(|entry| {
|
|
let entry = entry.unwrap_or_else(|err| panic!("read dir entry: {}", err));
|
|
let path = entry.path();
|
|
let extension = path.extension().and_then(OsStr::to_str)?;
|
|
if path.is_file() && extensions.contains(&extension) {
|
|
path.file_name().and_then(OsStr::to_str).map(str::to_string)
|
|
} else {
|
|
None
|
|
}
|
|
})
|
|
.collect()
|
|
}
|
|
|
|
fn assert_std_only_contains(source: &str, allowed: &[&str], context: &str) {
|
|
let mut remaining = source.to_string();
|
|
for name in allowed {
|
|
remaining = remaining.replace(name, "");
|
|
}
|
|
assert!(!remaining.contains("std."), "{}", context);
|
|
}
|
|
|
|
fn assert_deferred_json_surface_absent(source: &str, context: &str) {
|
|
for deferred in [
|
|
"parse_string",
|
|
"parse_object",
|
|
"parse_array",
|
|
"parse_value",
|
|
"tokenize",
|
|
"tokenizer",
|
|
"schema",
|
|
"stream",
|
|
"unicode",
|
|
"map",
|
|
] {
|
|
assert!(
|
|
!source.contains(deferred),
|
|
"{} must not claim deferred JSON `{}` policies",
|
|
context,
|
|
deferred
|
|
);
|
|
}
|
|
}
|
|
|
|
fn repo_root() -> PathBuf {
|
|
Path::new(env!("CARGO_MANIFEST_DIR"))
|
|
.parent()
|
|
.expect("compiler crate has repo parent")
|
|
.to_path_buf()
|
|
}
|
|
|
|
fn run_glagol<I, S>(args: I) -> Output
|
|
where
|
|
I: IntoIterator<Item = S>,
|
|
S: AsRef<std::ffi::OsStr>,
|
|
{
|
|
Command::new(env!("CARGO_BIN_EXE_glagol"))
|
|
.args(args)
|
|
.output()
|
|
.expect("run glagol")
|
|
}
|
|
|
|
fn run_glagol_in<I, S>(args: I, cwd: &Path) -> Output
|
|
where
|
|
I: IntoIterator<Item = S>,
|
|
S: AsRef<std::ffi::OsStr>,
|
|
{
|
|
Command::new(env!("CARGO_BIN_EXE_glagol"))
|
|
.args(args)
|
|
.current_dir(cwd)
|
|
.output()
|
|
.expect("run glagol")
|
|
}
|
|
|
|
fn run_glagol_configured<I, S, F>(args: I, configure: F) -> Output
|
|
where
|
|
I: IntoIterator<Item = S>,
|
|
S: AsRef<std::ffi::OsStr>,
|
|
F: FnOnce(&mut Command),
|
|
{
|
|
let mut command = Command::new(env!("CARGO_BIN_EXE_glagol"));
|
|
command.args(args);
|
|
configure(&mut command);
|
|
command.output().expect("run glagol")
|
|
}
|
|
|
|
fn configure_standard_local_env(command: &mut Command) {
|
|
command
|
|
.env_remove(STANDARD_ENV_MISSING_NAME)
|
|
.env(STANDARD_ENV_PRESENT_NAME, STANDARD_ENV_PRESENT_VALUE)
|
|
.env(
|
|
STANDARD_ENV_PRESENT_I32_NAME,
|
|
STANDARD_ENV_PRESENT_I32_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_ENV_PRESENT_U32_NAME,
|
|
STANDARD_ENV_PRESENT_U32_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_ENV_PRESENT_I64_NAME,
|
|
STANDARD_ENV_PRESENT_I64_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_ENV_PRESENT_U64_NAME,
|
|
STANDARD_ENV_PRESENT_U64_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_ENV_PRESENT_F64_NAME,
|
|
STANDARD_ENV_PRESENT_F64_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_ENV_PRESENT_BOOL_NAME,
|
|
STANDARD_ENV_PRESENT_BOOL_VALUE,
|
|
)
|
|
.env(STANDARD_ENV_INVALID_NAME, STANDARD_ENV_INVALID_VALUE);
|
|
}
|
|
|
|
fn configure_standard_import_env(command: &mut Command) {
|
|
command
|
|
.env_remove(STANDARD_IMPORT_ENV_MISSING_NAME)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_PRESENT_NAME,
|
|
STANDARD_IMPORT_ENV_PRESENT_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_PRESENT_I32_NAME,
|
|
STANDARD_IMPORT_ENV_PRESENT_I32_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_PRESENT_U32_NAME,
|
|
STANDARD_IMPORT_ENV_PRESENT_U32_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_PRESENT_I64_NAME,
|
|
STANDARD_IMPORT_ENV_PRESENT_I64_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_PRESENT_U64_NAME,
|
|
STANDARD_IMPORT_ENV_PRESENT_U64_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_PRESENT_F64_NAME,
|
|
STANDARD_IMPORT_ENV_PRESENT_F64_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_PRESENT_BOOL_NAME,
|
|
STANDARD_IMPORT_ENV_PRESENT_BOOL_VALUE,
|
|
)
|
|
.env(
|
|
STANDARD_IMPORT_ENV_INVALID_NAME,
|
|
STANDARD_IMPORT_ENV_INVALID_VALUE,
|
|
);
|
|
}
|
|
|
|
fn temp_root(name: &str) -> PathBuf {
|
|
let path =
|
|
std::env::temp_dir().join(format!("glagol-promotion-{}-{}", name, std::process::id()));
|
|
let _ = fs::remove_dir_all(&path);
|
|
fs::create_dir_all(&path).unwrap_or_else(|err| panic!("create `{}`: {}", path.display(), err));
|
|
path
|
|
}
|