From 2e119a0ae72d83f62f9742b174735d6944b6d29b Mon Sep 17 00:00:00 2001 From: Slava Pestov <slava@shill.local> Date: Mon, 31 Aug 2009 05:42:28 -0500 Subject: [PATCH 1/6] struct-arrays: hack it up so that if the class name is a literal parameter for the constructor, then the array works in deployed apps even if not every call site of nth or set-nth is inlined on the array. Fixes tools.deploy.test.5 regression after kqueue was converted to use STRUCT:. Because of Dan's call(-inlining, no perf regression on struct-arrays benchmark! --- basis/struct-arrays/struct-arrays.factor | 44 ++++++++++++++++-------- 1 file changed, 29 insertions(+), 15 deletions(-) diff --git a/basis/struct-arrays/struct-arrays.factor b/basis/struct-arrays/struct-arrays.factor index a3dcd98f0e..73eb356a60 100755 --- a/basis/struct-arrays/struct-arrays.factor +++ b/basis/struct-arrays/struct-arrays.factor @@ -1,7 +1,8 @@ ! Copyright (C) 2008 Slava Pestov. ! See http://factorcode.org/license.txt for BSD license. USING: accessors alien alien.c-types alien.structs byte-arrays -classes.struct kernel libc math parser sequences sequences.private ; +classes.struct kernel libc math parser sequences +sequences.private words fry memoize compiler.units ; IN: struct-arrays : c-type-struct-class ( c-type -- class ) @@ -11,7 +12,8 @@ TUPLE: struct-array { underlying c-ptr read-only } { length array-capacity read-only } { element-size array-capacity read-only } -{ class read-only } ; +{ class read-only } +{ ctor read-only } ; M: struct-array length length>> ; inline M: struct-array byte-length [ length>> ] [ element-size>> ] bi * ; inline @@ -20,34 +22,46 @@ M: struct-array byte-length [ length>> ] [ element-size>> ] bi * ; inline [ element-size>> * >fixnum ] [ underlying>> ] bi <displaced-alien> ; inline M: struct-array nth-unsafe - [ (nth-ptr) ] [ class>> dup struct-class? ] bi [ memory>struct ] [ drop ] if ; inline + [ (nth-ptr) ] [ ctor>> ] bi execute( alien -- object ) ; inline M: struct-array set-nth-unsafe [ (nth-ptr) swap ] [ element-size>> ] bi memcpy ; inline +! Foldable memo word. This is an optimization; by precompiling a +! constructor for array elements, we avoid memory>struct's slow path. +MEMO: struct-element-constructor ( c-type -- word ) + [ + "struct-array-ctor" f <word> + [ + swap dup struct-class? + [ '[ _ memory>struct ] [ ] like ] [ drop [ ] ] if + (( alien -- object )) define-inline + ] keep + ] with-compilation-unit ; foldable + +: <direct-struct-array> ( alien length c-type -- struct-array ) + [ heap-size ] [ c-type-struct-class ] [ struct-element-constructor ] + tri struct-array boa ; inline + M: struct-array new-sequence - [ element-size>> [ * (byte-array) ] 2keep ] - [ class>> ] bi struct-array boa ; inline + [ element-size>> * (byte-array) ] [ length>> ] [ class>> ] tri + <direct-struct-array> ; inline M: struct-array resize ( n seq -- newseq ) - [ [ element-size>> * ] [ underlying>> ] bi resize ] - [ [ element-size>> ] [ class>> ] bi ] 2bi - struct-array boa ; + [ [ element-size>> * ] [ underlying>> ] bi resize ] [ class>> ] 2bi + <direct-struct-array> ; inline : <struct-array> ( length c-type -- struct-array ) - [ heap-size [ * <byte-array> ] 2keep ] - [ c-type-struct-class ] bi struct-array boa ; inline + [ heap-size * <byte-array> ] 2keep <direct-struct-array> ; inline ERROR: bad-byte-array-length byte-array ; : byte-array>struct-array ( byte-array c-type -- struct-array ) - [ heap-size [ + [ + heap-size [ dup length ] dip /mod 0 = [ drop bad-byte-array-length ] unless - ] keep ] [ c-type-struct-class ] bi struct-array boa ; inline - -: <direct-struct-array> ( alien length c-type -- struct-array ) - [ heap-size ] [ c-type-struct-class ] bi struct-array boa ; inline + ] keep <direct-struct-array> ; inline : malloc-struct-array ( length c-type -- struct-array ) [ heap-size calloc ] 2keep <direct-struct-array> ; inline From ab45402d04b0591e127590007edb20dcaaf1cf20 Mon Sep 17 00:00:00 2001 From: Slava Pestov <slava@shill.local> Date: Mon, 31 Aug 2009 05:46:57 -0500 Subject: [PATCH 2/6] Minor doc improvements --- core/combinators/combinators-docs.factor | 20 +++++++++++++++++--- core/syntax/syntax-docs.factor | 10 +++++++++- 2 files changed, 26 insertions(+), 4 deletions(-) diff --git a/core/combinators/combinators-docs.factor b/core/combinators/combinators-docs.factor index 7395014bed..4a7fcea0e6 100755 --- a/core/combinators/combinators-docs.factor +++ b/core/combinators/combinators-docs.factor @@ -275,7 +275,7 @@ $nl "The simplest combinators do not take an effect declaration. The compiler checks the stack effect at compile time, rejecting the program if this cannot be done:" { $subsection call } { $subsection execute } -"The second set of combinators takes an effect declaration. The stack effect of the quotation or word is checked at runtime:" +"The second set of combinators takes an effect declaration. Note that the opening parenthesis is actually part of the word name; these are parsing words, and they read a stack effect until the corresponding closing parenthesis. The stack effect of the quotation or word is then checked at runtime:" { $subsection POSTPONE: call( } { $subsection POSTPONE: execute( } "The above are syntax sugar. The underlying words are a bit more verbose but allow non-constant effects to be passed in:" @@ -303,11 +303,25 @@ ABOUT: "combinators" HELP: call-effect { $values { "quot" quotation } { "effect" effect } } -{ $description "Given a quotation and a stack effect, calls the quotation, asserting at runtime that it has the given stack effect. This is a macro which expands given a literal effect parameter, and an arbitrary quotation which is not required at compile time." } ; +{ $description "Given a quotation and a stack effect, calls the quotation, asserting at runtime that it has the given stack effect. This is a macro which expands given a literal effect parameter, and an arbitrary quotation which is not required at compile time." } +{ $examples + "The following two lines are equivalent:" + { $code + "call( a b -- c )" + "(( a b -- c )) call-effect" + } +} ; HELP: execute-effect { $values { "word" word } { "effect" effect } } -{ $description "Given a word and a stack effect, executes the word, asserting at runtime that it has the given stack effect. This is a macro which expands given a literal effect parameter, and an arbitrary word which is not required at compile time." } ; +{ $description "Given a word and a stack effect, executes the word, asserting at runtime that it has the given stack effect. This is a macro which expands given a literal effect parameter, and an arbitrary word which is not required at compile time." } +{ $examples + "The following two lines are equivalent:" + { $code + "execute( a b -- c )" + "(( a b -- c )) execute-effect" + } +} ; HELP: execute-effect-unsafe { $values { "word" word } { "effect" effect } } diff --git a/core/syntax/syntax-docs.factor b/core/syntax/syntax-docs.factor index cc4b080491..50c7c047c7 100644 --- a/core/syntax/syntax-docs.factor +++ b/core/syntax/syntax-docs.factor @@ -834,6 +834,14 @@ HELP: call( HELP: execute( { $syntax "execute( stack -- effect )" } -{ $description "Calls the word on the top of the stack, asserting that it has the given stack effect. The word does not need to be known at compile time." } ; +{ $description "Calls the word on the top of the stack, asserting that it has the given stack effect. The word does not need to be known at compile time." } +{ $examples + { $code + "IN: scratchpad" + "" + ": eat ( -- ) ; : sleep ( -- ) ; : hack ( -- ) ;" + "{ eat sleep hack } [ execute( -- ) ] each" + } +} ; { POSTPONE: call( POSTPONE: execute( } related-words From 740856eeca04cb1839426c87263057e9cd36cbfc Mon Sep 17 00:00:00 2001 From: Doug Coleman <doug.coleman@gmail.com> Date: Mon, 31 Aug 2009 15:22:26 -0500 Subject: [PATCH 3/6] fix windows usings --- basis/windows/com/wrapper/wrapper.factor | 3 ++- basis/windows/ole32/ole32-tests.factor | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/basis/windows/com/wrapper/wrapper.factor b/basis/windows/com/wrapper/wrapper.factor index 3d78ccc849..2af416fb7e 100755 --- a/basis/windows/com/wrapper/wrapper.factor +++ b/basis/windows/com/wrapper/wrapper.factor @@ -3,7 +3,8 @@ init windows.com.syntax.private windows.com continuations kernel namespaces windows.ole32 libc vocabs assocs accessors arrays sequences quotations combinators math words compiler.units destructors fry math.parser generalizations sets -specialized-arrays.alien specialized-arrays.direct.alien ; +specialized-arrays.alien specialized-arrays.direct.alien +windows.kernel32 ; IN: windows.com.wrapper TUPLE: com-wrapper < disposable callbacks vtbls ; diff --git a/basis/windows/ole32/ole32-tests.factor b/basis/windows/ole32/ole32-tests.factor index aa02211ef3..c8358f5aa6 100644 --- a/basis/windows/ole32/ole32-tests.factor +++ b/basis/windows/ole32/ole32-tests.factor @@ -1,5 +1,6 @@ USING: kernel tools.test windows.ole32 alien.c-types -classes.struct specialized-arrays.uchar windows.kernel32 ; +classes.struct specialized-arrays.uchar windows.kernel32 +windows.com.syntax ; IN: windows.ole32.tests [ t ] [ From 23f34febbbbe57d5508416eacd5fefefe0f847ae Mon Sep 17 00:00:00 2001 From: Slava Pestov <slava@shill.local> Date: Mon, 31 Aug 2009 16:34:58 -0500 Subject: [PATCH 4/6] Fix image size regression with struct array tree shaking --- basis/struct-arrays/struct-arrays.factor | 11 +++++++---- basis/tools/deploy/shaker/shaker.factor | 12 +++++++++--- .../tools/deploy/shaker/strip-struct-arrays.factor | 13 +++++++++++++ 3 files changed, 29 insertions(+), 7 deletions(-) create mode 100644 basis/tools/deploy/shaker/strip-struct-arrays.factor diff --git a/basis/struct-arrays/struct-arrays.factor b/basis/struct-arrays/struct-arrays.factor index 73eb356a60..38dab33f0e 100755 --- a/basis/struct-arrays/struct-arrays.factor +++ b/basis/struct-arrays/struct-arrays.factor @@ -27,9 +27,7 @@ M: struct-array nth-unsafe M: struct-array set-nth-unsafe [ (nth-ptr) swap ] [ element-size>> ] bi memcpy ; inline -! Foldable memo word. This is an optimization; by precompiling a -! constructor for array elements, we avoid memory>struct's slow path. -MEMO: struct-element-constructor ( c-type -- word ) +: (struct-element-constructor) ( c-type -- word ) [ "struct-array-ctor" f <word> [ @@ -37,7 +35,12 @@ MEMO: struct-element-constructor ( c-type -- word ) [ '[ _ memory>struct ] [ ] like ] [ drop [ ] ] if (( alien -- object )) define-inline ] keep - ] with-compilation-unit ; foldable + ] with-compilation-unit ; + +! Foldable memo word. This is an optimization; by precompiling a +! constructor for array elements, we avoid memory>struct's slow path. +MEMO: struct-element-constructor ( c-type -- word ) + (struct-element-constructor) ; foldable : <direct-struct-array> ( alien length c-type -- struct-array ) [ heap-size ] [ c-type-struct-class ] [ struct-element-constructor ] diff --git a/basis/tools/deploy/shaker/shaker.factor b/basis/tools/deploy/shaker/shaker.factor index 6a133d9c87..2244eb9249 100755 --- a/basis/tools/deploy/shaker/shaker.factor +++ b/basis/tools/deploy/shaker/shaker.factor @@ -68,9 +68,14 @@ IN: tools.deploy.shaker ] when ; : strip-destructors ( -- ) - "libc" vocab [ - "Stripping destructor debug code" show - "vocab:tools/deploy/shaker/strip-destructors.factor" + "Stripping destructor debug code" show + "vocab:tools/deploy/shaker/strip-destructors.factor" + run-file ; + +: strip-struct-arrays ( -- ) + "struct-arrays" vocab [ + "Stripping dynamic struct array code" show + "vocab:tools/deploy/shaker/strip-struct-arrays.factor" run-file ] when ; @@ -493,6 +498,7 @@ SYMBOL: deploy-vocab : strip ( -- ) init-stripper strip-libc + strip-struct-arrays strip-destructors strip-call strip-cocoa diff --git a/basis/tools/deploy/shaker/strip-struct-arrays.factor b/basis/tools/deploy/shaker/strip-struct-arrays.factor new file mode 100644 index 0000000000..55b6630082 --- /dev/null +++ b/basis/tools/deploy/shaker/strip-struct-arrays.factor @@ -0,0 +1,13 @@ +USING: kernel stack-checker.transforms ; +IN: struct-arrays + +: struct-element-constructor ( c-type -- word ) + "Struct array usages must be compiled" throw ; + +<< + +\ struct-element-constructor [ + (struct-element-constructor) [ ] curry +] 1 define-transform + +>> \ No newline at end of file From 94c89e55e6e8cbf27898f62a18b7edcae29aed7b Mon Sep 17 00:00:00 2001 From: Slava Pestov <slava@shill.local> Date: Mon, 31 Aug 2009 16:48:10 -0500 Subject: [PATCH 5/6] tools.deploy.shaker: strip out call( and execute( runtime checking in a way that still allows the inlining optimization to work --- basis/tools/deploy/shaker/strip-call.factor | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/basis/tools/deploy/shaker/strip-call.factor b/basis/tools/deploy/shaker/strip-call.factor index d0593b6c15..0ecc22e4c0 100644 --- a/basis/tools/deploy/shaker/strip-call.factor +++ b/basis/tools/deploy/shaker/strip-call.factor @@ -1,10 +1,14 @@ ! Copyright (C) 2009 Slava Pestov ! See http://factorcode.org/license.txt for BSD license. -IN: tools.deploy.shaker.call - +USING: combinators.private kernel ; IN: combinators -USE: combinators.private -: call-effect ( word effect -- ) call-effect-unsafe ; inline +: call-effect ( word effect -- ) call-effect-unsafe ; -: execute-effect ( word effect -- ) execute-effect-unsafe ; inline \ No newline at end of file +: execute-effect ( word effect -- ) execute-effect-unsafe ; + +IN: compiler.tree.propagation.call-effect + +: call-effect-unsafe? ( quot effect -- ? ) 2drop t ; inline + +: execute-effect-unsafe? ( word effect -- ? ) 2drop t ; inline \ No newline at end of file From f6da4856b44903f0eec791c2305deb581536fc0b Mon Sep 17 00:00:00 2001 From: Slava Pestov <slava@shill.local> Date: Mon, 31 Aug 2009 17:07:24 -0500 Subject: [PATCH 6/6] benchmark.yuv-to-rgb: fix hints --- extra/benchmark/yuv-to-rgb/yuv-to-rgb.factor | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/extra/benchmark/yuv-to-rgb/yuv-to-rgb.factor b/extra/benchmark/yuv-to-rgb/yuv-to-rgb.factor index 561b6f0c0a..8041bef07f 100644 --- a/extra/benchmark/yuv-to-rgb/yuv-to-rgb.factor +++ b/extra/benchmark/yuv-to-rgb/yuv-to-rgb.factor @@ -86,7 +86,7 @@ STRUCT: yuv_buffer [ yuv>rgb-row ] with with each drop ; -HINTS: yuv>rgb byte-array byte-array ; +HINTS: yuv>rgb byte-array yuv_buffer ; : yuv>rgb-benchmark ( -- ) [ fake-data yuv>rgb ] with-destructors ;