Compare commits

...
42 Commits
Author SHA1 Message Date
Larry Gritz a0ea2668db CHANGES for release 2019-07-04 12:00:16 -07:00
marsupial 6ef53ccc64 Respect lockgeom default when building from commands. Remove ASSERT during ReParameter (#1032) 2019-07-02 23:58:24 -07:00
Larry Gritz 9b5cc9ba18 Port FindOpenEXR.cmake fixes from OIIO (#1022) 2019-05-22 12:19:25 -07:00
Larry Gritz 69d5c3e292 Bump version after release 2019-05-06 10:36:20 -07:00
Larry Gritz 6343afc07c CHANGES 2019-05-04 13:01:33 -07:00
Larry Gritz 3c957cf4ca Add build-time option to set gcc C++ ABI (ported from OIIO) (#995) 2019-04-16 09:26:24 -07:00
Larry Gritz bc0c58b49f Extend linearstep and smooth_linearstep to color/point/vector/normal (#994) 2019-04-16 09:25:49 -07:00
Larry Gritz bb92d7b8c3 oslc: slight adjustment to assignment typechecking (#993)
Consider int=float to be a warning, not an error.
This is partly because C allows it and we ran accross some
examples where it seems more strict than necessary.
(Of course it works without warning if you use a cast, showing
that any trucation is intentional.)
2019-04-10 16:49:25 -07:00
Larry Gritz 096005a6a4 Improve oslc type error detection for variable declaration with init
Turns out that some of the various type checking we do for simple
assignment,

    x = y

was not being checked at all for variable declaration with initialization,

    Type x = y

So this patch adds the necessary checks. And also goes back and improves
the error messages for regular variable assignment, changing from messages
like

    Cannot assign 'float' to 'int'

to the more clear (I think, because it names the variable, and looks
more like the grammatical construct being complained about)

    Cannot assign int i = float
2019-04-05 17:06:59 -07:00
Larry Gritz 14bbc14875 Bump version after release, and some minor README/CHANGES fixes. 2019-04-01 10:39:53 -07:00
Larry Gritz fd8ad23e85 CHANGES for release 2019-04-01 00:12:44 -07:00
Larry Gritz 02b84cfc90 Fix oslc assertion on type constructor for unknown struct (#988)
The assertion was not needed, errors issue before this code is reached.
2019-03-30 11:08:08 -07:00
Larry Gritz 7f750c900a Fix oslc assertion when passing init-lists to array parameters (#983)
It's easiest to explain the situation by example:

    void receive_array_3 (float array[3]) { }
    void receive_array_any (float array[]) { }

    receive_array_3 ({1.0, 2.0, 3.0});
    receive_array_any ({1.0, 2.0, 3.0});

Both of these would fail/crash by hitting an assertion in oslc.  The
general pattern is when passing an initializer-list (like just saying
`{ a, b, c }`) to a user function formal parameter that's an array.
They failed for somewhat different reasons if the formal parameter
was a concretely-sized array or if it was an unsized array.

A little bit of typecheck-fu handles this case.
2019-03-20 23:19:08 -07:00
Larry Gritz 156103daf2 Improve warnings about ill-advised use of comma operator (#978)
We previously had warnings that attempted to catch mistakes in using
the "comma operator" when the user intended an "aggregate type
constructor", for example:

    color x = (a, b, c);    // comma operator! equivalent to: x = c;
    color x = color(a,b,c); // this is what they probably meant

However, the way we implemented the warning was specific to assignment:

    x = (a, b, c);

and variable declaration with initialization:

    color x = (a, b, c);

But it missed similar bugs in other constructs, for example

    color x = Cdiffuse * (a, b, c);

Here the user surely intends to multiply Cdiffuse channel-by-channel
with color(a,b,c), but what they will actually get is Cfiffuse scaled
by float c.

This patch changes the strategy for this warning, no longer tied to
variable declaration or assignment, but more generally any time the
comma operator is used inside expression parentheses, it will give a
warning.
2019-03-14 10:59:02 -07:00
Larry Gritz bb89ec0afd Simplify flex/bison handling (#977)
Rely on CMake's own finding of flex/bison, simplifying our code to
just the helpful shortcut macro. Also make finding these REQUIRED,
which makes an easier-to-interpret error message than simply not
defining the macro.
2019-03-14 10:58:09 -07:00
Larry Gritz 51ebc17d43 Bump appveyor llvm release (and use pre-installed LLVM rather than building) 2019-03-12 13:44:22 -07:00
Larry Gritz a95a987b3a OptiX: always seem to need --cuda-path flag, even for cuda 9 2019-03-06 14:48:56 -08:00
Larry Gritz 18a1ee0e44 FindLLVM: Make more robust to library configuration of llvm (#976)
In particular, some system distributions bundle everything in one
libLLVM, without a separate libLLVMMCJIT.
2019-03-05 16:14:36 -08:00
aconty 69851a3159 Forbid LPE repetitions inside groups (#972)
This is not useful in practice and we've seen a case of exponential DFA
state blowup in issue #971 because of its accidental use. This does not
make LPEs totally robust to ReDoS but prevents this particular mistake.
2019-02-19 10:33:06 -08:00
Larry Gritz 1faae7e25c Bump version after release 2019-02-19 10:32:57 -08:00
Larry Gritz f8dc41c556 CHANGES 2019-02-01 11:55:58 -08:00
Larry Gritz cc70c2e37b Improve thread safety of OSLCompiler (#953)
Fixes #654.

There's a problem with the lock we use to protect the global
`oslcompiler` pointer -- it's locked for the duration `osl_parse_buffer`
(where it's assigned), but it is used and also cleared to NULL after the
lock is released (in particular, the clearing that happens in compile()
and compile_buffer().

The solution is to move the lock itself to compile/compile_buffer, and
do all of the assignment, use, and clear within the scope of that lock.

I think this went unnoticed for so long because most of us highly
multithread the shader execution (and runtime optimization), but not the
initial compilation -- except for Issue #654, and my sincere apologies for
letting that slip through the cracks.
2019-01-12 09:08:46 -08:00
Larry Gritz be86932223 Some C++ definition and other touch-ups (#950)
Some C++ definition and other touch-ups
Partly ported from equivalent changes in OIIO recently.
2019-01-12 09:02:26 -08:00
Larry Gritz 4019fadcb5 Fix custom namespace vs symbol hiding clash
I guess everbody who builds with NAMESPACE=... to customize OSL's namespace
must (like we do) pick a name that include the substring "OSL".
Because if they don't... a bunch of public API symbols will be improperly
hidden!

Oops. Seems like the most foolproof solution is that if a custom namespace
is supplied that doesn't include the substring "OSL", have the build
script prepend "OSL_". Then the symbol hiding regex will work.

(You may object: "But then you're not using exactly what they asked for!"
Correct, but remember we are already overriding their literal choice by
automatically appending the OSL version number as well.)

While there, also take care to hide symbols containing "pvt", which I
think should not be exposed, despite the fact that they're in the main
OSL namespace.
2019-01-11 14:13:47 -08:00
Larry Gritz 6d99c3b943 Get rid of suspicious spurious reference (#959) 2019-01-04 16:35:49 -08:00
Larry Gritz befa64183c Fix transformc with derivs when using OCIO (#960)
I have no idea how this ever worked. In fact, it must never have, because
our checked-in reference output was wrong. But it kept matching the same
wrong until it didn't, and became a different kind of wrong on at least
one machine.

When doing transformc, where the space names necessitated using OCIO for
the transformation math, and only for the derivative case (the non-deriv
was fine all along), we were simply passing the wrong stride parameters
to the colorproc->apply() call.

Also, I noticed that we were trying to save a per-context "last
transformation" to avoid the lookup when doing repeats of needing the
same colorproc (basically, a 1-item LRU cached lookup of the
colorproc). But we never saved the space name, so the cache was not
operating.
2019-01-04 16:34:26 -08:00
Larry Gritz 78f8480c07 Reword error with less yelling (#952)
Fixes #811
2019-01-04 10:46:40 -08:00
Larry Gritz 1dfef8bc49 Fix bug with inverse spline (#954)
We were clipping the range incorrectly for bezier, where it needs
to step by 3 CVs for each span. Worked ok for the other spline
types, which step by 1.

Add a test that verify that a spline designed to give a f(x)=x response
does so, and also that its inverse is perfect.

Fixes #778
2019-01-04 10:46:08 -08:00
Larry Gritz 6d34914ccc Fix bug in oslc loop code generation (#947)
The problem was specific to using an integer variable directly as the
loop test, rather than a comparison. So for example, this would work
fine:

    i = 3;
    while (i > 0) {
        --i;
    }

But this would loop forever:

    i = 3;
    while (i) {
        --i;
    }

Because of a hilarious chain of events, this would eventually lead to
the optimizer thinking that since the value of i was nonzero at the
beginning of the loop, it must be equivalent to while(1). There was a
subtle assumption that the scope of the loop control variable would be
entirey inside the condition code. That was true of the the temporary
created to hold the result of "i > 0", but not true of the direct use of
i itself.  The solution is to force it to create a bool comparison
(which turns into the same machine code later anyway, so there is no
efficiency issue here).

Fixes #776
2019-01-04 10:46:04 -08:00
Larry Gritz 99297424d9 oslc: Fix crash when encountering for (;;) (#951)
An empty conditional clause of a `for` statement was leading to bad
things. It's understood that `for (;;)` means `for (;1;)`, so just
make sure that happens when parsing.

Fixes #688
2019-01-04 10:45:58 -08:00
Larry Gritz 4678327640 Fix group_name, group_init_name, group_entry_name (#957)
I didn't notice this in Tim's code before today, but he made the
retrieval of these group attributes more complex than they needed to be.
Instead of messing with pointers (which we avoid), you can just directly
getattribute(name,string&). So now we use that. Also eliminate group_name
entirely, since it's redundant with the existing groupname.
2019-01-04 08:22:57 -08:00
Larry Gritz d782bcead3 Change %.8g formatting to %.9g (#949)
%.9g is needed to totally guarantee full precision preservation for all
possible float32 values.
2019-01-03 11:59:15 -08:00
Larry Gritz e2f20d0a00 Tweaks to pdf docs building 2018-12-23 13:20:44 -08:00
marsupial fa657029cb Fix array initialization counter (#948) 2018-12-18 23:08:15 -08:00
Larry Gritz 44516d0c4f Improve oso output efficiency with less redundant work on retrieve_source (#938)
To make debugging easier and be more human-readable, oso files are
littered with comment lines reproducing the source code, so that you can
see which source corresponds to which "oso assembly".

The workhorse here is the retrieve_source(filename,line) function. But
it was unspeakably inefficient, reading the entire source file every
time an op needed a different source file than the previous op, and
scanning the file to find the n-th line *every* time. This seems like
the lookup is O(n^2) and also that we're rereading source files
potentially thousands of times.

Theory: If we cache all the files we read, so we never read each source
file more than once, and also remember which line we used last (we tend
to go in increasing order in a source file) and resume the search from
there, backtracking only when the line is less than the last one needed,
it ought to be blazingly fast!

Practice: It barely makes any difference.  Compiling all 600 MaterialX
source osl files takes 30 seconds on my laptop, and this fix saves maybe
a second or two at most.

Oh well. But I already made the change, so may as well keep the more
efficient algorithm. Perhaps there are other cases where it gives a
bigger advantage.
2018-12-13 09:19:49 -08:00
Larry Gritz 7de8a0f3a4 testshade: check that no leftover errors are in the TS or IC (#939) 2018-12-13 09:19:49 -08:00
Larry Gritz 5fed2f2fe7 Docs typo fix
[ci skip]
2018-12-13 09:19:49 -08:00
Larry Gritz 899b1b31cc Demote writing to non-output function parameters to be a warning. (#944)
It was never supposed to be allowed. It used to be ignored in most
cases, error neither detected nor issued. PR #878 "fixed" it to detect
the error. But there were too many shaders that did it, users are
confused and it breaks things.

So this patch downgrades it from an error to a warning. If you ignore
the warning, you get what you deserve (which is probably not
bad... people lived with it for years). Anybody who wants it to be fully
illegal can always compile with -Werror to turn warnings in to full
errors.

I also "uniformized" two separate error messages on the same general
topic, so they look the same.
2018-12-13 09:18:09 -08:00
Larry Gritz 9c2c9b0eb0 Bump version after release 2018-12-13 09:17:57 -08:00
Larry Gritz 550096985e Extremely minor docs source fix 2018-12-05 11:50:39 -08:00
Larry Gritz 64c2d66a39 Release 1.10 2018-12-01 18:01:58 -08:00
Larry Gritz 53469220b4 Docs touch-ups and prepare release candidate 2018-11-26 15:27:13 -08:00
66 changed files with 896 additions and 359 deletions
+88
View File
@@ -1,3 +1,80 @@
Release 1.10.6 -- Jul 4, 2019 (compared to 1.10.5)
--------------------------------------------------
* Build: Fixes to FindOpenEXR.cmake. #1022
* ShadingSystem: when building a shader group from serialized commands,
respect the global lockgeom default. #1032
Release 1.10.5 -- May 1, 2019 (compared to 1.10.4)
--------------------------------------------------
* Extend linearstep() and smooth_linearstep() to work with color, point,
vector, and normal types (previously restricted to float). #994
* Improve oslc type error detection for variable declarations with init
expressions. Note that this may flag some warnings and errors that went
undetected before, involving initialization assignments of incompatible
types. #991, #993
* Add a build-time option GLIBCXX_USE_CXX11_ABI to force the "new/old string
ABI" to something other than the default for your version of gcc. #995
Release 1.10.4 -- Apr 1, 2019 (compared to 1.10.3)
--------------------------------------------------
* LPEs: forbid LPE repetitions inside groups. #972
* Build process: build script finding of LLVM is now more robust to certain
library configurations of llvm, particularly where everything is bundled
in just one libLLVM without a separate libLLVMMCJIT. #976
* oslc: Improve warnings about ill-advised use of the comma operator. #978
* oslc: Fix an assertion/crash when passing initialization-lists as
parameters to a function, where the function argument expected was as
array. #983
* oslc: Fix an assertion/crash for certain type constructors of structs,
where the struct name was not declared. (This is an incorrect shader,
but of course should have issued an error, not crashed.) #988
* Note: The experimental OptiX path is not expected to work in this branch!
Development has continued in the 'master' branch. If you are interested in
testing the OptiX support while it's under development, please do so with
the master branch, because fixes and improvements to the OptiX support
are not being backported to the 1.10 branch.
* Tested and verified that everything builds and works correctly with
Clang 8 and LLVM 8.0.
Release 1.10.3 -- Feb 1, 2019 (compared to 1.10.2)
--------------------------------------------------
* oslc: Writing to function parameters not marked as `output` was only
recently properly recognized as an error (it was documented as illegal
all along). Now we demote to a warning, treating it as a full error was
too disruptive. #944 (1.10.3)
* testshade: Check that no leftover errors are in the TextureSystem or
ImageCache at the end of the test (that would indicate that someplace in
OSL we are failing to check texture errors). #939 (1.10.3)
* Improve oso output efficiency. #938 (1.10.3)
* oslc: Fix bug related to counting the proper number of values used for
array default value initialization. #948 (1.10.3)
* oslc: Slight modification to the formatting of floating point values in
the oso file to ensure full precision preservation for float values.
#949 (1.10.3)
* oslc: Fix crash when encountering empty-expression `for (;;)`. #951 (1.10.3)
* oslc: Fix bug in code generation of certain `while` loops that directly
tested a variable as a zero/nonzero test, such as:
```
i = 3;
while (i)
--i;
```
whereas the following had worked (they should have been identical):
```
i = 3;
while (i != 0)
--i;
```
#947 (1.10.3/1.11.0)
* Fix bug in implementation of `splineinverse()` when computing with
Bezier interpolation. #954 (1.10.3)
* Fix bug in implementation of `transformc` when relyin on OpenColorIO for
color transformation math, in cases were derivatives were needed (this
is a rare case probably nobody ran into). #960 (1.10.3)
* Improve thread-safety of the OSLCompiler itself, in case an app wants
to be compiling several shaders to oso concurrently by different threads.
#953 (1.10.3)
Release 1.10 -- Dec 1, 2018 (compared to 1.9)
--------------------------------------------------
Dependency and standards changes:
@@ -152,6 +229,11 @@ API changes, new options, new ShadingSystem features (for renderer writers):
* Older versions of RendererServices texture functions, the old ones
with no errormessage parameter, which were documented as deprecated
since 1.8, are now marked OSL_DEPRECATED. #832 (1.10.0)
* OSLCompiler API:
* Improved error reporting when compiling from memory buffer. The
`OSLCompiler::compile_buffer()` method now takes an optional filename
parameter that will make error messages attribute the right "file"
(e.g., `Error: foo.osl:5...` rather than `<buffer>:5...`). #937 (1.10.2)
* Miscellaneous:
* liboslnoise: Properly hide/export symbols. #849 (1.10.0/1.9.7)
* The behavior of the "searchpath:shader" attribute, used for finding
@@ -214,6 +296,12 @@ Documentation:
Release 1.9.13 -- 1 Dec 2018 (compared to 1.9.12)
------------------------------------------------
* Fix crash with texture3d lookups with derivatives. #932
* Fix oslc crash when a struct parameter is initialized with a function call
that returns a structure. #934
Release 1.9.12 -- 1 Nov 2018 (compared to 1.9.11)
------------------------------------------------
* Fix oslc read/write error for `regex_search`/`regex_match` #922
+13 -6
View File
@@ -1,13 +1,13 @@
cmake_minimum_required (VERSION 3.2.2)
cmake_policy (SET CMP0048 NEW) # Allow VERSION specifier in project()
project (OSL
VERSION 1.10.2
VERSION 1.10.6
LANGUAGES CXX C)
set (PROJ_NAME ${PROJECT_NAME}) # short name
string (TOLOWER ${PROJ_NAME} PROJ_NAME_LOWER) # short name lower case
set (PROJECT_VERSION_RELEASE_TYPE "beta") # "dev", "betaX", "RCY", ""
set (PROJECT_VERSION_RELEASE_TYPE "") # "dev", "betaX", "RCY", ""
set (${PROJECT_NAME}_VERSION_RELEASE_TYPE ${PROJECT_VERSION_RELEASE_TYPE})
set (PROJECT_COPYRIGHTYEARS "2008-2018")
set (PROJECT_COPYRIGHTYEARS "2008-2019")
set (PROJECT_AUTHORS "Sony Pictures Imageworks, et al")
set (PROJECT_URL "")
@@ -119,8 +119,13 @@ else ()
endif ()
# Set the default namespace
# Set the default namespace. For symbol hiding reasons, it's important that
# the project name is a subset of the namespace name.
set (PROJ_NAMESPACE "${${PROJ_NAME}_NAMESPACE}")
string(REGEX MATCH ${PROJECT_NAME} NAMESPACE_HAS_PROJECT_NAME ${PROJ_NAMESPACE})
if (NOT NAMESPACE_HAS_PROJECT_NAME)
set (PROJ_NAMESPACE ${PROJECT_NAME}_${PROJ_NAMESPACE})
endif ()
set (PROJ_NAMESPACE_V "${PROJ_NAMESPACE}_v${PROJECT_VERSION_MAJOR}_${PROJECT_VERSION_MINOR}")
message(STATUS "Setting Namespace to: ${PROJ_NAMESPACE_V}")
@@ -288,7 +293,8 @@ TESTSUITE ( aastep allowconnect-err and-or-not-synonyms arithmetic
pnoise pnoise-cell pnoise-gabor pnoise-perlin
operator-overloading
oslc-comma oslc-D
oslc-err-arrayindex oslc-err-closuremul oslc-err-field
oslc-err-arrayindex oslc-err-assignmenttypes
oslc-err-closuremul oslc-err-field
oslc-err-format oslc-err-funcoverload
oslc-err-intoverflow oslc-err-write-nonoutput
oslc-err-noreturn oslc-err-notfunc
@@ -296,6 +302,7 @@ TESTSUITE ( aastep allowconnect-err and-or-not-synonyms arithmetic
oslc-err-outputparamvararray oslc-err-paramdefault
oslc-err-struct-array-init oslc-err-struct-ctr
oslc-err-struct-dup oslc-err-struct-print
oslc-err-unknown-ctr
oslc-warn-commainit
oslc-variadic-macro
oslc-version
@@ -309,7 +316,7 @@ TESTSUITE ( aastep allowconnect-err and-or-not-synonyms arithmetic
render-background render-bumptest
render-cornell render-furnace-diffuse
render-microfacet render-oren-nayar render-veachmis render-ward
select shortcircuit spline splineinverse
select shortcircuit spline splineinverse splineinverse-ident
spline-boundarybug spline-derivbug
string
struct struct-array struct-array-mixture
+5 -4
View File
@@ -9,11 +9,12 @@ Dependencies
OSL requires the following dependencies or tools.
NEW or CHANGED dependencies since the last major release are **bold**.
* Build system: [CMake](https://cmake.org/) 3.2.2 or newer
* Build system: [CMake](https://cmake.org/) 3.2.2 or newer (tested through
3.14)
* A suitable C++11 compiler to build OSL itself, which may be any of:
- GCC 4.8.5 or newer (through gcc 8)
- Clang 3.4 or newer (through clang 7)
- Clang 3.4 or newer (through clang 8)
- Microsoft Visual Studio 2015 or newer
- Intel C++ compiler icc version 13 (?) or newer
@@ -39,14 +40,14 @@ NEW or CHANGED dependencies since the last major release are **bold**.
DYLD_LIBRARY_PATH on OS X) and then OSL's build scripts will be able
to find it.
* **[LLVM](http://www.llvm.org) 4.0, 5.0, 6.0, or 7.0**
* **[LLVM](http://www.llvm.org) 4.0, 5.0, 6.0, 7.0, or 8.0**
Optionally, if Clang libraries are installed alongside LLVM, OSL will
in most circumstances use Clang's internals for C-style preprocessing of
OSL source. If not found, it will fall back on Boost Wave (but on many
platforms, that requires that Boost has been built in C++11 mode).
* [Boost](www.boost.org) 1.55 or newer.
* [Boost](www.boost.org) 1.55 or newer (tested through 1.69).
* [Ilmbase/OpenEXR](http://openexr.com/downloads.html) 2.0 or newer
* [Flex](https://github.com/westes/flex) and
[GNU Bison](https://www.gnu.org/software/bison/)
+1 -1
View File
@@ -1,4 +1,4 @@
Copyright (c) 2009-2017 Sony Pictures Imageworks Inc., et al.
Copyright (c) 2009-2019 Sony Pictures Imageworks Inc., et al.
All Rights Reserved.
Redistribution and use in source and binary forms, with or without
+5
View File
@@ -187,6 +187,10 @@ ifneq (${USE_LIBCPLUSPLUS},)
MY_CMAKE_FLAGS += -DUSE_LIBCPLUSPLUS:BOOL=${USE_LIBCPLUSPLUS}
endif
ifneq (${GLIBCXX_USE_CXX11_ABI},)
MY_CMAKE_FLAGS += -DGLIBCXX_USE_CXX11_ABI=${GLIBCXX_USE_CXX11_ABI}
endif
ifneq (${EXTRA_CPP_ARGS},)
MY_CMAKE_FLAGS += -DEXTRA_CPP_ARGS:STRING="${EXTRA_CPP_ARGS}"
endif
@@ -373,6 +377,7 @@ help:
@echo " MYCC=xx MYCXX=yy Use custom compilers"
@echo " USE_CPP=14 Compile in C++14 mode (default is C++11)"
@echo " USE_LIBCPLUSPLUS=1 Use clang libc++"
@echo " GLIBCXX_USE_CXX11_ABI=1 For gcc, use the new string ABI"
@echo " EXTRA_CPP_ARGS= Additional args to the C++ command"
@echo " USE_NINJA=1 Set up Ninja build (instead of make)"
@echo " USE_CCACHE=0 Disable ccache (even if available)"
+19 -2
View File
@@ -306,7 +306,7 @@ Films using OSL (grouped by year of release date):
Coco,
Justice League,
Thor: Ragnarok
* **(2018) / upcoming**
* **(2018)**
Peter Rabbit,
Black Panther,
Annnihilation,
@@ -315,6 +315,7 @@ Films using OSL (grouped by year of release date):
Avengers Infinity War,
Deadpool 2,
Incredibles 2,
Jurassic World: Fallen Kingdom,
Hotel Transylvania 3: Summer Vacation,
Ant Man and the Wasp,
Skyscraper,
@@ -325,8 +326,24 @@ Films using OSL (grouped by year of release date):
Alpha,
Venom,
First Man,
Bad Times at the El Royale,
Fantastic Beasts: The Crimes of Grindelwald,
Spider-Man: Into the Spider-Verse,
Bohemian Rhapsody,
Holmes and Watson,
Spider-Man: Into the Spider-Verse
* **(2019 / upcoming)**
The Kid Who Would Be King,
Alita: Battle Angel,
Lego Movie 2,
Lucky 13,
Captain Marvel,
Avengers: Endgame,
Pokémon Detective Pikachu,
Godzilla: King of Monsters,
Rim of the World,
Men in Black International,
Toy Story 4,
Spider-Man: Far From Home,
...
+11 -8
View File
@@ -42,6 +42,7 @@ before_build:
$OSL_INSTALL_BEGIN=Get-Date
Write-Output "Configuration: $env:CONFIGURATION"
Write-Output "Platform: $env:PLATFORM"
ls C:\Libraries\llvm-5.0.0
Get-ChildItem Env:
[Array]$OSL_BUILD_FLAGS = "--", "/nologo", "/verbosity:minimal";
@@ -50,8 +51,8 @@ before_build:
$DEP_DIR = "C:\projects\OSLdeps"
$BOOST_ROOT = "C:\Libraries\boost_1_63_0"
$PYTHON_DIR = "C:\Python27"
$LLVM_DIR = "C:\Libraries\llvm-4.0.0"
$LLVM_DIR = "$DEP_DIR"
$LLVM_DIR = "C:\Libraries\llvm-5.0.0"
#$LLVM_DIR = "$DEP_DIR"
$env:Path += ";$DEP_DIR\lib;$DEP_DIR\bin"
$OSL_INT_DIR = "build\windows$env:PLATFORM"
@@ -121,6 +122,14 @@ before_build:
cmake ..\.. -G "$GENERATOR" -DCMAKE_CONFIGURATION_TYPES="$env:CONFIGURATION" -DCMAKE_PREFIX_PATH="$DEP_DIR" -DCMAKE_INSTALL_PREFIX="$DEP_DIR" -DCMAKE_CXX_FLAGS=" /W1 /EHsc /DWIN32=1 "
cmake --build . --config $env:CONFIGURATION --target INSTALL $OSL_BUILD_FLAGS
# LLVM
# This shouldn't be necessary, we use the pre-installed LLVM
# cd $DWN_DIR
# git clone --depth 10 --branch release_40 https://github.com/llvm-mirror/llvm.git
# cd llvm; md "$OSL_INT_DIR" -Force | Out-Null; cd "$OSL_INT_DIR"
# cmake ..\.. -G "$GENERATOR" -DCMAKE_CONFIGURATION_TYPES="$env:CONFIGURATION" -DCMAKE_PREFIX_PATH="$DEP_DIR" -DCMAKE_INSTALL_PREFIX="$DEP_DIR" -DLLVM_TARGETS_TO_BUILD="X86"
# cmake --build . --config $env:CONFIGURATION --target INSTALL $OSL_BUILD_FLAGS
# OpenEXR
cd $DWN_DIR
Start-FileDownload http://download.savannah.nongnu.org/releases/openexr/openexr-2.2.1.tar.gz
@@ -128,12 +137,6 @@ before_build:
cmake ..\.. -G "$GENERATOR" -DCMAKE_CONFIGURATION_TYPES="$env:CONFIGURATION" -DCMAKE_PREFIX_PATH="$DEP_DIR" -DCMAKE_INSTALL_PREFIX="$DEP_DIR" -DILMBASE_PACKAGE_PREFIX="$DEP_DIR" -DCMAKE_CXX_FLAGS=" /W1 /EHsc /DWIN32=1 "
cmake --build . --config $env:CONFIGURATION --target INSTALL $OSL_BUILD_FLAGS
# LLVM
cd $DWN_DIR
git clone --depth 10 --branch release_40 https://github.com/llvm-mirror/llvm.git
cd llvm; md "$OSL_INT_DIR" -Force | Out-Null; cd "$OSL_INT_DIR"
cmake ..\.. -G "$GENERATOR" -DCMAKE_CONFIGURATION_TYPES="$env:CONFIGURATION" -DCMAKE_PREFIX_PATH="$DEP_DIR" -DCMAKE_INSTALL_PREFIX="$DEP_DIR" -DLLVM_TARGETS_TO_BUILD="X86"
cmake --build . --config $env:CONFIGURATION --target INSTALL $OSL_BUILD_FLAGS
}
# Always do this
+12 -4
View File
@@ -11,19 +11,19 @@ BASEDIR=`pwd`
pwd
echo "EXR install dir will be: ${EXRINSTALLDIR}"
if [ ! -e ${EXRINSTALLDIR} ] ; then
if [[ ! -e ${EXRINSTALLDIR} ]] ; then
mkdir -p ${EXRINSTALLDIR}
fi
# Clone OpenEXR project (including IlmBase) from GitHub and build
if [ ! -e ./ext/openexr ] ; then
if [[ ! -e ./ext/openexr ]] ; then
echo "git clone ${EXRREPO} ./ext/openexr"
git clone ${EXRREPO} ./ext/openexr
fi
flags=
if [ ${LINKSTATIC:=0} == 1 ] ; then
if [[ ${LINKSTATIC:=0} == 1 ]] ; then
flags=${flags} --enable-static --enable-shared=no --with-pic
fi
@@ -31,7 +31,7 @@ pushd ./ext/openexr
echo "git checkout ${EXRBRANCH} --force"
git checkout ${EXRBRANCH} --force
if [ ${EXRBRANCH} == "v2.3.0" ] ; then
if [[ ${EXRBRANCH} == "v2.3.0" ]] ; then
# Simplified setup for 2.3+
mkdir build
cd build
@@ -64,3 +64,11 @@ ls -R ${EXRINSTALLDIR}
#echo "listing .."
#ls ..
# Set up paths. These will only affect the caller if this script is
# run with 'source' rather than in a separate shell.
export ILMBASE_ROOT_DIR=$EXRINSTALLDIR
export OPENEXR_ROOT_DIR=$EXRINSTALLDIR
export ILMBASE_LIBRARY_DIR=$EXRINSTALLDIR/lib
export OPENEXR_LIBRARY_DIR=$EXRINSTALLDIR/lib
export LD_LIBRARY_PATH=$OPENEXR_ROOT_DIR/lib:$LD_LIBRARY_PATH
+1 -1
View File
@@ -1,4 +1,4 @@
{
global: *OSL*; test_shade; *osl*imageio*; *osl_input_extensions;
local: osl_*; *;
local: osl_*; *pvt*; *;
};
+13
View File
@@ -21,6 +21,7 @@ option (CLANG_TIDY "Enable clang-tidy" OFF)
set (CLANG_TIDY_CHECKS "-*" CACHE STRING "clang-tidy checks to perform")
set (CLANG_TIDY_ARGS "" CACHE STRING "clang-tidy args")
option (CLANG_TIDY_FIX "Have clang-tidy fix source" OFF)
set (GLIBCXX_USE_CXX11_ABI "" CACHE STRING "For gcc, use the new C++11 library ABI (0|1)")
# Figure out which compiler we're using
@@ -196,6 +197,18 @@ if (USE_LIBCPLUSPLUS AND CMAKE_COMPILER_IS_CLANG)
set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -stdlib=libc++")
endif ()
# GCC 5+: honor build-time option for whether or not to use new string ABI.
# FIXME: In theory, this should also be needed for clang, if compiling with
# the gcc libstdc++ toolchain. In practice, I could not get things to build
# with clang properly when using this option, and I haven't yet seen a case
# where it's needed. We can return to this and fix for clang if it becomes a
# legit problem later.
if (CMAKE_COMPILER_IS_GNUCC AND NOT ${GCC_VERSION} VERSION_LESS 5.0)
if (NOT ${GLIBCXX_USE_CXX11_ABI} STREQUAL "")
add_definitions ("-D_GLIBCXX_USE_CXX11_ABI=${GLIBCXX_USE_CXX11_ABI}")
endif ()
endif ()
# SIMD and machine architecture options
set (SIMD_COMPILE_FLAGS "")
+1 -10
View File
@@ -238,16 +238,7 @@ if (USE_CUDA OR USE_OPTIX)
message (FATAL_ERROR "CUDA ${CUDA_VERSION} requires LLVM 6.0 or greater")
endif ()
# TODO: When compiling for CUDA 9.0+ using clang, specifying the CUDA
# path can result in multiply-defined symbol errors; for CUDA 8.0,
# not defining it results in undefined symbols. It would be better
# if there were a more robust and unified way to handle this, but
# this will have to do for now.
if (${CUDA_VERSION_MAJOR} GREATER 8)
set (CUDA_LIB_FLAGS "")
else ()
set (CUDA_LIB_FLAGS "--cuda-path=${CUDA_TOOLKIT_ROOT_DIR}")
endif ()
set (CUDA_LIB_FLAGS "--cuda-path=${CUDA_TOOLKIT_ROOT_DIR}")
endif ()
# end CUDA setup
+28 -58
View File
@@ -1,8 +1,7 @@
# LG's macros for using flex and bison.
# Merely including this file will set FLEX_EXECUTABLE and BISON_EXECUTABLE
# to the locations of 'flex' and 'bison' on the system, and leave them
# undefined if those programs were not found.
# If both are found, there will also be a macro defined:
# Merely including this file will require flex and bison to be found.
#
# The main purpose is to define the macro FLEX_BISON:
# FLEX_BISON ( flexsrc bisonsrc srclist compiler_headers )
# where
# flexsrc = the name of the .l file
@@ -14,77 +13,48 @@
# for the .y and .l files.
IF (NOT FLEX_EXECUTABLE)
if (NOT Flex_FIND_QUIETLY)
MESSAGE (STATUS "Looking for flex")
endif ()
FIND_PROGRAM (FLEX_EXECUTABLE flex)
IF (FLEX_EXECUTABLE)
if (NOT Flex_FIND_QUIETLY)
MESSAGE (STATUS "Looking for flex -- ${FLEX_EXECUTABLE}")
endif ()
ENDIF (FLEX_EXECUTABLE)
ENDIF (NOT FLEX_EXECUTABLE)
find_package (BISON REQUIRED)
find_package (FLEX REQUIRED)
IF (NOT BISON_EXECUTABLE)
if (NOT Bison_FIND_QUIETLY)
MESSAGE (STATUS "Looking for bison")
endif ()
FIND_PROGRAM (BISON_EXECUTABLE bison)
IF (BISON_EXECUTABLE)
if (NOT Bison_FIND_QUIETLY)
MESSAGE (STATUS "Looking for bison -- ${BISON_EXECUTABLE}")
endif ()
ENDIF (BISON_EXECUTABLE)
ENDIF (NOT BISON_EXECUTABLE)
IF ( FLEX_EXECUTABLE AND BISON_EXECUTABLE )
MACRO ( FLEX_BISON flexsrc bisonsrc prefix srclist compiler_headers )
if ( FLEX_EXECUTABLE AND BISON_EXECUTABLE )
macro ( FLEX_BISON flexsrc bisonsrc prefix srclist compiler_headers )
if (VERBOSE)
MESSAGE (STATUS "FLEX_BISON flex=${flexsrc} bison=${bisonsrc} prefix=${prefix}")
message (STATUS "FLEX_BISON flex=${flexsrc} bison=${bisonsrc} prefix=${prefix}")
endif ()
#MESSAGE (STATUS " src ${CMAKE_CURRENT_SOURCE_DIR}")
#MESSAGE (STATUS " bin ${CMAKE_CURRENT_BINARY_DIR}")
GET_FILENAME_COMPONENT ( bisonsrc_we ${bisonsrc} NAME_WE )
SET ( bisonoutputcxx "${CMAKE_CURRENT_BINARY_DIR}/${bisonsrc_we}.cpp" )
SET ( bisonoutputh "${CMAKE_CURRENT_BINARY_DIR}/${bisonsrc_we}.h" )
# MESSAGE (STATUS " bison output ${bisonoutputcxx} ${bisonoutputh}")
get_filename_component ( bisonsrc_we ${bisonsrc} NAME_WE )
set ( bisonoutputcxx "${CMAKE_CURRENT_BINARY_DIR}/${bisonsrc_we}.cpp" )
set ( bisonoutputh "${CMAKE_CURRENT_BINARY_DIR}/${bisonsrc_we}.h" )
GET_FILENAME_COMPONENT ( flexsrc_we ${flexsrc} NAME_WE )
SET ( flexoutputcxx "${CMAKE_CURRENT_BINARY_DIR}/${flexsrc_we}.cpp" )
# MESSAGE (STATUS " flex output ${flexoutputcxx}")
SET ( ${srclist} ${${srclist}} ${bisonoutputcxx} ${flexoutputcxx} )
# MESSAGE (STATUS " src list now ${${srclist}}")
# MESSAGE (STATUS " compiler headers = ${${compiler_headers}}")
get_filename_component ( flexsrc_we ${flexsrc} NAME_WE )
set ( flexoutputcxx "${CMAKE_CURRENT_BINARY_DIR}/${flexsrc_we}.cpp" )
set ( ${srclist} ${${srclist}} ${bisonoutputcxx} ${flexoutputcxx} )
# Be really sure that we prefer the FlexLexer.h that comes with
# the flex binary we're using, not some other one in the system.
GET_FILENAME_COMPONENT ( FLEX_UP ${FLEX_EXECUTABLE} PATH )
GET_FILENAME_COMPONENT ( FLEX_UP_UP ${FLEX_UP} PATH )
SET ( FLEX_INCLUDE_DIR "${FLEX_UP_UP}/include" )
get_filename_component ( FLEX_UP ${FLEX_EXECUTABLE} PATH )
get_filename_component ( FLEX_UP_UP ${FLEX_UP} PATH )
set ( FLEX_INCLUDE_DIR "${FLEX_UP_UP}/include" )
if (VERBOSE)
MESSAGE (STATUS "Flex include dir = ${FLEX_INCLUDE_DIR}")
message (STATUS "Flex include dir = ${FLEX_INCLUDE_DIR}")
endif ()
INCLUDE_DIRECTORIES ( ${FLEX_INCLUDE_DIR} )
include_directories ( ${FLEX_INCLUDE_DIR} )
INCLUDE_DIRECTORIES ( ${CMAKE_CURRENT_BINARY_DIR} )
INCLUDE_DIRECTORIES ( ${CMAKE_CURRENT_SOURCE_DIR} )
ADD_CUSTOM_COMMAND ( OUTPUT ${bisonoutputcxx}
# include_directories ( ${CMAKE_CURRENT_BINARY_DIR} )
include_directories ( ${CMAKE_CURRENT_SOURCE_DIR} )
add_custom_command ( OUTPUT ${bisonoutputcxx}
COMMAND ${BISON_EXECUTABLE} -dv -p ${prefix} -o ${bisonoutputcxx} "${CMAKE_CURRENT_SOURCE_DIR}/${bisonsrc}"
MAIN_DEPENDENCY ${bisonsrc}
DEPENDS ${${compiler_headers}}
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} )
if ( WINDOWS )
SET ( WINCOMPAT --wincompat )
set ( FB_WINCOMPAT --wincompat )
else ()
SET ( WINCOMPAT )
set ( FB_WINCOMPAT )
endif ()
ADD_CUSTOM_COMMAND ( OUTPUT ${flexoutputcxx}
COMMAND ${FLEX_EXECUTABLE} ${WINCOMPAT} -o ${flexoutputcxx} "${CMAKE_CURRENT_SOURCE_DIR}/${flexsrc}"
add_custom_command ( OUTPUT ${flexoutputcxx}
COMMAND ${FLEX_EXECUTABLE} ${FB_WINCOMPAT} -o ${flexoutputcxx} "${CMAKE_CURRENT_SOURCE_DIR}/${flexsrc}"
MAIN_DEPENDENCY ${flexsrc}
DEPENDS ${${compiler_headers}}
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} )
ENDMACRO ()
ENDIF ()
endmacro ()
endif ()
+4 -20
View File
@@ -52,19 +52,10 @@ execute_process (COMMAND ${LLVM_CONFIG} --includedir
execute_process (COMMAND ${LLVM_CONFIG} --targets-built
OUTPUT_VARIABLE LLVM_TARGETS
OUTPUT_STRIP_TRAILING_WHITESPACE)
if (NOT ${LLVM_VERSION} VERSION_LESS 3.8)
execute_process (COMMAND ${LLVM_CONFIG} --system-libs
OUTPUT_VARIABLE LLVM_SYSTEM_LIBRARIES
OUTPUT_STRIP_TRAILING_WHITESPACE)
string (REPLACE " " ";" LLVM_SYSTEM_LIBRARIES "${LLVM_SYSTEM_LIBRARIES}")
else ()
# Older LLVM did not have llvm-config --system-libs, but we know that
# on Linux, we'll need curses.
find_package (Curses)
if (CURSES_FOUND)
list (APPEND LLVM_SYSTEM_LIBRARIES ${CURSES_LIBRARIES})
endif ()
endif ()
execute_process (COMMAND ${LLVM_CONFIG} --system-libs
OUTPUT_VARIABLE LLVM_SYSTEM_LIBRARIES
OUTPUT_STRIP_TRAILING_WHITESPACE)
string (REPLACE " " ";" LLVM_SYSTEM_LIBRARIES "${LLVM_SYSTEM_LIBRARIES}")
find_library ( LLVM_LIBRARY
NAMES LLVM-${LLVM_VERSION} LLVM
@@ -73,7 +64,6 @@ find_library ( LLVM_MCJIT_LIBRARY
NAMES LLVMMCJIT
PATHS ${LLVM_LIB_DIR})
foreach (COMPONENT clangFrontend clangDriver clangSerialization
clangParse clangSema clangAnalysis clangAST clangBasic
clangEdit clangLex)
@@ -86,12 +76,6 @@ foreach (COMPONENT clangFrontend clangDriver clangSerialization
endforeach ()
# if (NOT LLVM_LIBRARY)
# execute_process (COMMAND ${LLVM_CONFIG} --libfiles engine
# OUTPUT_VARIABLE LLVM_LIBRARIES
# OUTPUT_STRIP_TRAILING_WHITESPACE)
# endif ()
# shared llvm library may not be available, this is not an error if we use LLVM_STATIC.
if ((LLVM_LIBRARY OR LLVM_LIBRARIES OR LLVM_STATIC) AND LLVM_INCLUDES AND LLVM_DIRECTORY AND LLVM_LIB_DIR)
if (LLVM_STATIC)
+15 -5
View File
@@ -25,8 +25,12 @@ endif ()
# Attempt to find OpenEXR with pkgconfig
find_package(PkgConfig)
if (PKG_CONFIG_FOUND)
pkg_check_modules(_ILMBASE QUIET IlmBase>=2.0.0)
pkg_check_modules(_OPENEXR QUIET OpenEXR>=2.0.0)
if (NOT ILMBASE_ROOT_DIR)
pkg_check_modules(_ILMBASE QUIET IlmBase>=2.0.0)
endif ()
if (NOT OPENEXR_ROOT_DIR)
pkg_check_modules(_OPENEXR QUIET OpenEXR>=2.0.0)
endif ()
endif (PKG_CONFIG_FOUND)
# List of likely places to find the headers -- note priority override of
@@ -60,7 +64,11 @@ find_path (OPENEXR_INCLUDE_PATH OpenEXR/OpenEXRConfig.h
find_path (OPENEXR_INCLUDE_PATH OpenEXR/OpenEXRConfig.h)
# Try to figure out version number
if (EXISTS "${OPENEXR_INCLUDE_PATH}/OpenEXR/ImfMultiPartInputFile.h")
if (DEFINED _OPENEXR_VERSION AND NOT "${_OPENEXR_VERSION}" STREQUAL "")
set (OPENEXR_VERSION "${_OPENEXR_VERSION}")
string (REGEX REPLACE "([0-9]+)\\.[0-9\\.]+" "\\1" OPENEXR_VERSION_MAJOR "${_OPENEXR_VERSION}")
string (REGEX REPLACE "[0-9]+\\.([0-9]+)(\\.[0-9]+)?" "\\1" OPENEXR_VERSION_MINOR "${_OPENEXR_VERSION}")
elseif (EXISTS "${OPENEXR_INCLUDE_PATH}/OpenEXR/ImfMultiPartInputFile.h")
# Must be at least 2.0
file(STRINGS "${OPENEXR_INCLUDE_PATH}/OpenEXR/OpenEXRConfig.h" TMP REGEX "^#define OPENEXR_VERSION_STRING .*$")
string (REGEX MATCHALL "[0-9]+[.0-9]+" OPENEXR_VERSION ${TMP})
@@ -93,6 +101,8 @@ set (GENERIC_LIBRARY_PATHS
/opt/local/lib
$ENV{PROGRAM_FILES}/OpenEXR/lib/static )
# message (STATUS "Generic lib paths: ${GENERIC_LIBRARY_PATHS}")
# Handle request for static libs by altering CMAKE_FIND_LIBRARY_SUFFIXES.
# We will restore it at the end of this file.
set (_openexr_orig_suffixes ${CMAKE_FIND_LIBRARY_SUFFIXES})
@@ -114,14 +124,14 @@ foreach (COMPONENT ${_openexr_components})
# First try with the version embedded
set (FULL_COMPONENT_NAME ${COMPONENT}-${OPENEXR_VERSION_MAJOR}_${OPENEXR_VERSION_MINOR})
find_library (OPENEXR_${UPPERCOMPONENT}_LIBRARY ${FULL_COMPONENT_NAME}
PATHS ${OPENEXR_LIBRARY_DIR}
PATHS ${OPENEXR_LIBRARY_DIR} $ENV{OPENEXR_LIBRARY_DIR}
${GENERIC_LIBRARY_PATHS} NO_DEFAULT_PATH)
# Again, with no directory restrictions
find_library (OPENEXR_${UPPERCOMPONENT}_LIBRARY ${FULL_COMPONENT_NAME})
# Try again without the version
set (FULL_COMPONENT_NAME ${COMPONENT})
find_library (OPENEXR_${UPPERCOMPONENT}_LIBRARY ${FULL_COMPONENT_NAME}
PATHS ${OPENEXR_LIBRARY_DIR}
PATHS ${OPENEXR_LIBRARY_DIR} $ENV{OPENEXR_LIBRARY_DIR}
${GENERIC_LIBRARY_PATHS} NO_DEFAULT_PATH)
# One more time, with no restrictions
find_library (OPENEXR_${UPPERCOMPONENT}_LIBRARY ${FULL_COMPONENT_NAME})
+9 -3
View File
@@ -6,7 +6,7 @@ all: languagespec.pdf
# document making rule: use pdflatex
languagespec.pdf: *.tex languagespec.aux macros.aux Figures/*.pdf Figures/*png
languagespec.pdf: *.tex Figures/*.pdf Figures/*png
pdflatex ${PDFLATEX_FLAGS} languagespec.tex
@@ -15,8 +15,14 @@ languagespec.pdf: *.tex languagespec.aux macros.aux Figures/*.pdf Figures/*png
index: languagespec_index
languagespec_index:
pdflatex ${PDFLATEX_FLAGS} languagespec.tex
pdflatex ${PDFLATEX_FLAGS} languagespec.tex
makeindex languagespec
pdflatex ${PDFLATEX_FLAGS} languagespec.tex
pdflatex ${PDFLATEX_FLAGS} languagespec.tex languagespec.aux macros.aux
pdflatex ${PDFLATEX_FLAGS} languagespec.tex languagespec.aux macros.aux languagespec.toc
clean:
rm -f languagespec.aux languagespec.idx languagespec.ilg languagespec.ind languagespec.log
rm -f languagespec.out languagespec.pdf languagespec.toc macros.aux
.PHONY: clean
+13 -6
View File
@@ -61,7 +61,7 @@ Editor: Larry Gritz \\
\emph{lg@imageworks.com}
}
\date{{\large Date: 31 Mar 2018 \\
(with corrections, 1 Nov 2018)
(with corrections, 12 Apr 2019)
}
\bigskip
\bigskip
@@ -3448,11 +3448,15 @@ The \emph{type} may be any of of \float, \color, \point, \vector, or
performed component-by-component (separately for $x$, $y$, and $z$).
\apiend
\apiitem{float {\ce linearstep} (float edge0, float edge1, float x)}
\apiitem{float {\ce linearstep} (float edge0, float edge1, float x) \\
\emph{type} {\ce linearstep} (\emph{type} edge0, \emph{type} edge1, \emph{type} x)}
\indexapi{linearstep()}
Returns 0 if $x \le {\mathit edge0}$, and 1 if $x \ge {\mathit edge1}$,
and performs a linear
interpolation between 0 and 1 when ${\mathit edge0} < x < {\mathit edge1}$.
This is equivalent to {\cf step(edge0, x)} when {\cf edge0 == edge1}.
For \color and \point-like types, the computations are
performed component-by-component (separately for $x$, $y$, and $z$).
\apiend
\apiitem{float {\ce smoothstep} (float edge0, float edge1, float x) \\
@@ -3466,10 +3470,11 @@ with a smooth transition.
The \emph{type} may be any of of \float, \color, \point, \vector, or
\normal. For \color and \point-like types, the computations are
performed component-by-component (separately for $x$, $y$, and $z$).
performed component-by-component.
\apiend
\apiitem{float {\ce smooth_linearstep} (float edge0, float edge1, float x, float eps)}
\apiitem{float {\ce smooth_linearstep} (float edge0, float edge1, float x, float eps) \\
\emph{type} {\ce smooth_linearstep} (\emph{type} edge0, \emph{type} edge1, \emph{type} x, \emph{type} eps)}
\indexapi{smooth_linearstep()}
This function is strictly linear between ${\mathit edge0}+{\mathit eps}$ and ${\mathit edge1}-{\mathit eps}$
but smoothly ramps to 0 between ${\mathit edge0}-{\mathit eps}$ and ${\mathit edge0}+{\mathit eps}$
@@ -3477,6 +3482,8 @@ and smoothly ramps to 1 between ${\mathit edge1}-{\mathit eps}$ and ${\mathit ed
It is 0 when $x \le {\mathit edge0}-{\mathit eps}$, and 1 if $x \ge {\mathit edge1}+{\mathit eps}$,
and performs a linear
interpolation between 0 and 1 when ${\mathit edge0} < x < {\mathit edge1}$.
For \color and \point-like types, the computations are
performed component-by-component.
\apiend
@@ -4038,7 +4045,7 @@ Identical to {\cf regex_search}, except that it must match the
Perform a texture lookup of an image file, indexed by 2D coordinates
$(s,t)$, antialiased over a region defined by the differentials
\emph{dsdx, dtdx, dsty} and \emph{dtdy} (which are computed
\emph{dsdx, dtdx, dsdy} and \emph{dtdy} (which are computed
automatically from $s$ and $t$, if not supplied). Whether the results
are assigned to a \float or a \color (or type cast to one of those)
determines whether the texture lookup is a single channel or three
@@ -4937,7 +4944,7 @@ wish to make queryable.
\apiend
\begin{table}[htbp]
\caption{Names of standard attributes that may be retrieved.}\label{tab:cameraattributes}
\caption{Names of standard attributes that may be retrieved.}\label{tab:stdattributes}
\begin{tabular}{|p{1.8in}|p{0.6in}|p{2.8in}|}
\hline
{\bf Name} & {\bf Type} & {\bf Description} \\
+33 -10
View File
@@ -44,12 +44,23 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// same if another packages is compiling against OSL and using these headers
// (OSL may be C++11 but the client package may be older, or vice versa --
// use these two symbols to differentiate these cases, when important).
#if (__cplusplus >= 201402L)
# define OSL_CPLUSPLUS_VERSION 14
#if (__cplusplus >= 201703L)
# define OSL_CPLUSPLUS_VERSION 17
# define OSL_CONSTEXPR14 constexpr
# define OSL_CONSTEXPR17 constexpr
# define OSL_CONSTEXPR20 /* not constexpr before C++20 */
#elif (__cplusplus >= 201402L)
# define OSL_CPLUSPLUS_VERSION 14
# define OSL_CONSTEXPR14 constexpr
# define OSL_CONSTEXPR17 /* not constexpr before C++17 */
# define OSL_CONSTEXPR20 /* not constexpr before C++20 */
#elif (__cplusplus >= 201103L) || _MSC_VER >= 1900
# define OSL_CPLUSPLUS_VERSION 11
# define OSL_CPLUSPLUS_VERSION 11
# define OSL_CONSTEXPR14 /* not constexpr before C++14 */
# define OSL_CONSTEXPR17 /* not constexpr before C++17 */
# define OSL_CONSTEXPR20 /* not constexpr before C++20 */
#else
# error "This version of OSL requires C++11"
# error "This version of OSL requires C++11"
#endif
#ifndef OSL_HOSTDEVICE
@@ -153,16 +164,28 @@ using OIIO::string_view;
#endif
#ifndef __has_attribute
# define __has_attribute(x) 0
// In C++20 (and some compilers before that), __has_cpp_attribute can
// test for understand of [[attr]] tests.
#ifndef __has_cpp_attribute
# define __has_cpp_attribute(x) 0
#endif
#if OSL_CPLUSPLUS_VERSION >= 14 && __has_attribute(deprecated)
// On gcc & clang, __has_attribute can test for __attribute__((attr))
#ifndef __has_attribute
# define __has_attribute(x) 0
#endif
// In C++17 (and some compilers before that), __has_include("blah.h") or
// __has_include(<blah.h>) can test for presence of an include file.
#ifndef __has_include
# define __has_include(x) 0
#endif
#if OSL_CPLUSPLUS_VERSION >= 14 || __has_cpp_attribute(deprecated)
# define OSL_DEPRECATED(msg) [[deprecated(msg)]]
#elif (defined(__GNUC__) && OIIO_GNUC_VERSION >= 40600) || defined(__clang__)
#elif defined(__GNUC__) || defined(__clang__) || __has_attribute(deprecated)
# define OSL_DEPRECATED(msg) __attribute__((deprecated(msg)))
#elif defined(__GNUC__) /* older gcc -- only the one with no message */
# define OSL_DEPRECATED(msg) __attribute__((deprecated))
#elif defined(_MSC_VER)
# define OSL_DEPRECATED(msg) __declspec(deprecated(msg))
#else
+3 -1
View File
@@ -67,7 +67,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
OSL_LIBRARY_VERSION_PATCH, \
OSL_LIBRARY_VERSION_RELEASE_TYPE)
#define OSL_INTRO_STRING "OpenShadingLanguage " OSL_LIBRARY_VERSION_STRING
#define OSL_COPYRIGHT_STRING "(c) Copyright 2009-2017 Sony Pictures Imageworks, et al. All rights reserved."
#define OSL_COPYRIGHT_STRING "(c) Copyright 2009-2019 Sony Pictures Imageworks, et al. All rights reserved."
// Version numbers for the compiled shader format. The major number
@@ -97,5 +97,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#cmakedefine01 OSL_BUILD_CPP14
// OSL_BUILD_CPP17 will be 1 if this OSL was built using C++17
#cmakedefine01 OSL_BUILD_CPP17
// OSL_BUILD_CPP20 will be 1 if this OSL was built using C++20 or higher
#cmakedefine01 OSL_BUILD_CPP20
#endif /* OSLVERSION_H */
+20 -7
View File
@@ -318,11 +318,11 @@ ASTshader_declaration::ASTshader_declaration (OSLCompilerImpl *comp,
ASSERT (arg->nodetype() == variable_declaration_node);
ASTvariable_declaration *v = (ASTvariable_declaration *)arg;
if (! v->init())
v->error ("shader parameter '%s' MUST have a default initializer",
v->name().c_str());
v->error ("shader parameter '%s' requires a default initializer",
v->name());
if (v->is_output() && v->typespec().is_unsized_array())
v->error ("shader output parameter '%s' can't be unsized array",
v->name().c_str());
v->name());
}
}
@@ -859,6 +859,18 @@ ASTconditional_statement::childname (size_t i) const
ASTloop_statement::ASTloop_statement (OSLCompilerImpl *comp, LoopType looptype,
ASTNode *init, ASTNode *cond,
ASTNode *iter, ASTNode *stmt)
: ASTNode (loop_statement_node, comp, looptype, init, cond, iter, stmt)
{
// Handle empty comparison, for(;;), is same as for(;1;)
if (!cond)
m_children[1] = new ASTliteral(comp, 1);
}
const char *
ASTloop_statement::childname (size_t i) const
{
@@ -943,10 +955,11 @@ ASTNode::check_symbol_writeability (ASTNode *var)
if (dest) {
if (dest->readonly()) {
if (OSL_VERSION >= 11001)
error ("cannot write to \"%s\" (read-only symbol)", dest->name());
else
warning ("cannot write to \"%s\" (read-only symbol)", dest->name());
warning ("cannot write to non-output parameter \"%s\"", dest->name());
// Note: Consider it only a warning to write to a non-output
// parameter. Users who want it to be a hard error can use
// -Werror. Writing to any other readonly symbols is a full
// error.
return false;
}
} else {
+2 -4
View File
@@ -655,9 +655,7 @@ public:
};
ASTloop_statement (OSLCompilerImpl *comp, LoopType looptype, ASTNode *init,
ASTNode *cond, ASTNode *iter, ASTNode *stmt)
: ASTNode (loop_statement_node, comp, looptype, init, cond, iter, stmt)
{ }
ASTNode *cond, ASTNode *iter, ASTNode *stmt);
const char *nodetypename () const { return "loop_statement"; }
const char *childname (size_t i) const;
@@ -913,7 +911,7 @@ public:
/// Pointer to the ASTfunction_declaration node that defines the user
/// function, or NULL if it's not a user-defined function.
ASTfunction_declaration * user_function () const {
return (ASTfunction_declaration *) func()->node();
return func() ? (ASTfunction_declaration *) func()->node() : nullptr;
}
private:
+21 -12
View File
@@ -472,8 +472,16 @@ ASTcompound_initializer::codegen (Symbol *sym)
return codegen_struct_initializers (initlist(), sym, true /*is_constructor*/);
}
ASSERT(0 && "compound codegen");
return NULL;
if (m_typespec.is_sized_array()) {
if (!sym)
sym = m_compiler->make_temporary (m_typespec);
codegen_initlist (initlist(), m_typespec, sym);
return sym;
}
error("Possible compiler bug: compound_initializer codegen does not "
"know how to handle type %s", typespec());
return nullptr;
}
@@ -657,7 +665,7 @@ ASTNode::one_default_literal (const Symbol *sym, ASTNode *init,
if (islit && lit->typespec().is_int())
out += Strutil::format ("%d", lit->intval());
else if (islit && lit->typespec().is_float())
out += Strutil::format ("%.8g", lit->floatval());
out += Strutil::format ("%.9g", lit->floatval());
else {
out += "0"; // FIXME?
completed = false;
@@ -665,10 +673,10 @@ ASTNode::one_default_literal (const Symbol *sym, ASTNode *init,
} else if (type.is_triple()) {
if (islit && lit->typespec().is_int()) {
float f = lit->intval();
out += Strutil::format ("%.8g%s%.8g%s%.8g", f, sep, f, sep, f);
out += Strutil::format ("%.9g%s%.9g%s%.9g", f, sep, f, sep, f);
} else if (islit && lit->typespec().is_float()) {
float f = lit->floatval();
out += Strutil::format ("%.8g%s%.8g%s%.8g", f, sep, f, sep, f);
out += Strutil::format ("%.9g%s%.9g%s%.9g", f, sep, f, sep, f);
} else if (init && init->typespec() == type &&
(init->nodetype() == ASTNode::type_constructor_node ||
(init->nodetype() == ASTNode::compound_initializer_node &&
@@ -697,9 +705,9 @@ ASTNode::one_default_literal (const Symbol *sym, ASTNode *init,
}
}
if (nargs == 1)
out += Strutil::format ("%.8g%s%.8g%s%.8g", f[0], sep, f[0], sep, f[0]);
out += Strutil::format ("%.9g%s%.9g%s%.9g", f[0], sep, f[0], sep, f[0]);
else
out += Strutil::format ("%.8g%s%.8g%s%.8g", f[0], sep, f[1], sep, f[2]);
out += Strutil::format ("%.9g%s%.9g%s%.9g", f[0], sep, f[1], sep, f[2]);
} else {
out += Strutil::format ("0%s0%s0", sep, sep);
completed = false;
@@ -708,12 +716,12 @@ ASTNode::one_default_literal (const Symbol *sym, ASTNode *init,
if (islit && lit->typespec().is_int()) {
float f = lit->intval();
for (int c = 0; c < 16; ++c)
out += Strutil::format ("%.8g%s", (c/4)==(c%4) ? f : 0.0f,
out += Strutil::format ("%.9g%s", (c/4)==(c%4) ? f : 0.0f,
c<15 ? sep.c_str() : "");
} else if (islit && lit->typespec().is_float()) {
float f = lit->floatval();
for (int c = 0; c < 16; ++c)
out += Strutil::format ("%.8g%s", (c/4)==(c%4) ? f : 0.0f,
out += Strutil::format ("%.9g%s", (c/4)==(c%4) ? f : 0.0f,
c<15 ? sep.c_str() : "");
} else if (init && init->typespec() == type &&
init->nodetype() == ASTNode::type_constructor_node) {
@@ -741,11 +749,11 @@ ASTNode::one_default_literal (const Symbol *sym, ASTNode *init,
}
if (nargs == 1) {
for (int c = 0; c < 16; ++c)
out += Strutil::format ("%.8g%s", (c/4)==(c%4) ? f[0] : 0.0f,
out += Strutil::format ("%.9g%s", (c/4)==(c%4) ? f[0] : 0.0f,
c<15 ? sep.c_str() : "");
} else {
for (int c = 0; c < 16; ++c)
out += Strutil::format ("%.8g%s", f[c], c<15 ? sep.c_str() : "");
out += Strutil::format ("%.9g%s", f[c], c<15 ? sep.c_str() : "");
}
} else {
for (int c = 0; c < 16; ++c)
@@ -1414,7 +1422,8 @@ ASTloop_statement::codegen (Symbol *)
codegen_list (init());
int condlabel = m_compiler->next_op_label ();
Symbol *condvar = cond()->codegen_int ();
Symbol *condvar = cond()->codegen_int (/*dest=*/ nullptr,
/*boolify=*/ true);
// Retroactively add the argument
size_t argstart = m_compiler->add_op_args (1, &condvar);
+67 -17
View File
@@ -116,7 +116,8 @@ OSLCompiler::output_filename () const
namespace pvt { // OSL::pvt
OSLCompilerImpl *oslcompiler = NULL;
OSLCompilerImpl *oslcompiler = nullptr;
static std::mutex oslcompiler_mutex;
static ustring op_for("for");
static ustring op_while("while");
@@ -312,7 +313,7 @@ OSLCompilerImpl::preprocess_buffer (const std::string &buffer,
new clang::DiagnosticsEngine(diagIDs, diagOptions, diagPrinter);
inst.setDiagnostics(diagEngine);
const std::shared_ptr<clang::TargetOptions> &targetopts =
const std::shared_ptr<clang::TargetOptions> targetopts =
std::make_shared<clang::TargetOptions>(inst.getTargetOpts());
targetopts->Triple = llvm::sys::getDefaultTargetTriple();
clang::TargetInfo *target =
@@ -535,6 +536,7 @@ OSLCompilerImpl::compile (string_view filename,
std::vector<std::string> includepaths;
m_cwd = OIIO::Filesystem::current_path();
m_main_filename = filename;
clear_filecontents_cache();
read_compile_options (options, defines, includepaths);
@@ -557,6 +559,9 @@ OSLCompilerImpl::compile (string_view filename,
} else if (m_preprocess_only) {
std::cout << preprocess_result;
} else {
// Thread safety with the lexer/parser
std::lock_guard<std::mutex> lock (oslcompiler_mutex);
oslcompiler = this;
bool parseerr = osl_parse_buffer (preprocess_result);
if (! parseerr) {
if (shader())
@@ -599,7 +604,7 @@ OSLCompilerImpl::compile (string_view filename,
ASSERT (m_osofile == NULL);
}
oslcompiler = NULL;
oslcompiler = nullptr;
}
return ! error_encountered();
@@ -623,6 +628,7 @@ OSLCompilerImpl::compile_buffer (string_view sourcecode,
m_cwd = OIIO::Filesystem::current_path();
m_main_filename = filename;
clear_filecontents_cache();
// Determine where the installed shader include directory is, and
// look for ../shaders/stdosl.h and force it to include.
@@ -639,6 +645,9 @@ OSLCompilerImpl::compile_buffer (string_view sourcecode,
} else if (m_preprocess_only) {
std::cout << preprocess_result;
} else {
// Thread safety with the lexer/parser
std::lock_guard<std::mutex> lock (oslcompiler_mutex);
oslcompiler = this;
bool parseerr = osl_parse_buffer (preprocess_result);
if (! parseerr) {
if (shader())
@@ -677,7 +686,7 @@ OSLCompilerImpl::compile_buffer (string_view sourcecode,
ASSERT (m_osofile == NULL);
}
oslcompiler = NULL;
oslcompiler = nullptr;
}
return ! error_encountered();
@@ -770,10 +779,10 @@ OSLCompilerImpl::write_oso_const_value (const ConstantSymbol *sym) const
oso ("%d%s", sym->intval(i), nelements>1 ? " " : "");
else if (elemtype == TypeDesc::FLOAT)
for (int i = 0; i < nelements; ++i)
oso ("%.8g%s", sym->floatval(i), nelements>1 ? " " : "");
oso ("%.9g%s", sym->floatval(i), nelements>1 ? " " : "");
else if (equivalent (elemtype, TypeDesc::TypeVector))
for (int i = 0; i < nelements; ++i)
oso ("%.8g %.8g %.8g%s", sym->vecval(i)[0], sym->vecval(i)[1],
oso ("%.9g %.9g %.9g%s", sym->vecval(i)[0], sym->vecval(i)[1],
sym->vecval(i)[2], nelements>1 ? " " : "");
else {
ASSERT (0 && "Don't know how to output this constant type");
@@ -1039,29 +1048,70 @@ OSLCompilerImpl::write_oso_file (const std::string &outfilename,
std::string
void
OSLCompilerImpl::clear_filecontents_cache()
{
m_filecontents_map.clear();
m_last_sourcefile.clear();
m_last_filecontents = nullptr;
m_last_sourceline = 1; // note we call the first line "1" for users
m_last_sourceline_offset = 0;
}
string_view
OSLCompilerImpl::retrieve_source (ustring filename, int line)
{
// If we don't already have the file open, open it
if (filename != m_last_sourcefile) {
bool ok = OIIO::Filesystem::read_text_file (filename, m_filecontents);
if (ok) {
m_last_sourcefile = filename;
// If we don't have a valid "last", look it up in the cache.
if (filename != m_last_sourcefile || !m_last_filecontents) {
m_last_sourceline = 1;
m_last_sourceline_offset = 0;
auto found = m_filecontents_map.find (filename);
if (found == m_filecontents_map.end()) {
// If it wasn't in the cache, read the file and add it.
std::string contents;
bool ok = OIIO::Filesystem::read_text_file (filename, contents);
if (ok) {
m_last_sourcefile = filename;
m_filecontents_map[filename] = std::move(contents);
m_last_filecontents = &m_filecontents_map[filename];
} else {
m_last_sourcefile = ustring();
m_last_filecontents = nullptr;
return "<file not found>";
}
} else {
m_last_sourcefile = ustring();
return "<file not found>";
m_last_sourcefile = filename;
m_last_filecontents = &found->second;
}
}
// Now read lines up to and including the file we want.
OIIO::string_view s (m_filecontents);
OIIO::string_view s (*m_last_filecontents);
int orig_sourceline = line;
if (line >= m_last_sourceline) {
// Shortcut: the line we want is in the same file as the last read,
// and at least as far in the file. Start the search from where we
// left off last time.
s.remove_prefix (m_last_sourceline_offset);
line -= m_last_sourceline - 1;
} else {
// If we have to backtrack at all, backtrack to the file start.
m_last_sourceline_offset = 0;
m_last_sourceline = 1;
}
size_t offset = m_last_sourceline_offset;
for ( ; line > 1; --line) {
size_t p = s.find_first_of ('\n');
if (p == OIIO::string_view::npos)
return "<line not found>";
s.remove_prefix (p+1);
offset += p+1;
}
s = s.substr (0, s.find_first_of ('\n'));
m_last_sourceline_offset = offset;
m_last_sourceline = orig_sourceline;
return s;
}
@@ -1164,8 +1214,8 @@ OSLCompilerImpl::check_write_legality (const Opcode &op, int opnum,
if (sym->symtype() == SymTypeParam &&
(opnum < sym->initbegin() || opnum >= sym->initend())) {
error (op.sourcefile(), op.sourceline(),
"Cannot write to input parameter '%s' (op %d)",
sym->name().c_str(), opnum);
"cannot write to non-output parameter \"%s\"",
sym->name());
}
}
+12 -3
View File
@@ -454,7 +454,12 @@ private:
return NULL;
return static_cast<ASTshader_declaration *>(m_shader.get());
}
std::string retrieve_source (ustring filename, int line);
// Retrieve the particular line of a file.
string_view retrieve_source (ustring filename, int line);
// Clear internal caches that speed up retrieve_source().
void clear_filecontents_cache();
ustring m_filename; ///< Current file we're parsing
int m_lineno; ///< Current line we're parsing
@@ -480,8 +485,6 @@ private:
int m_next_const; ///< Next const symbol index
std::vector<ConstantSymbol *> m_const_syms; ///< All consts we've made
std::ostream *m_osofile; ///< Open .oso stream for output
std::string m_filecontents; ///< Contents of source file
ustring m_last_sourcefile;///< Last filename for retrieve_source
ustring m_codegenmethod; ///< Current method we're generating code for
std::stack<FunctionSymbol *> m_function_stack; ///< Stack of called funcs
int m_total_nesting; ///< total conditional nesting level (0 == none)
@@ -491,6 +494,12 @@ private:
int m_main_method_start; ///< Instruction where 'main' starts
bool m_declaring_shader_formals; ///< Are we declaring shader formals?
std::set<std::pair<ustring,int>> m_nowarn_lines; ///< Lines for 'nowarn'
typedef std::unordered_map<ustring,std::string,ustringHash> FCMap;
FCMap m_filecontents_map; ///< Contents of source files we've seen
ustring m_last_sourcefile;///< Last filename for retrieve_source
std::string* m_last_filecontents = nullptr; //< Last file contents
int m_last_sourceline;
size_t m_last_sourceline_offset;
};
+15 -1
View File
@@ -796,7 +796,21 @@ expression
$$->sourceline (@1.first_line);
}
}
| '(' compound_expression ')' { $$ = $2; }
| '(' compound_expression ')'
{
if ($2->nodetype() == ASTNode::comma_operator_node) {
// Warning for comma operator ïn parenthesized
// expressions, which sometimes happens when somebody
// forgets the proper syntax for triple constructors:
// color x = Cd * (a, b, c); // same as: x = Cd * c
// when they really meant
// color x = Cd * color(a, b, c);
oslcompiler->warning(oslcompiler->filename(),
@1.first_line,
"Comma operator inside parenthesis is probably an error -- it is not a vector/color.");
}
$$ = $2;
}
| function_call
| assign_expression
| ternary_expression
+2 -4
View File
@@ -381,9 +381,8 @@ namespace pvt { // OSL::pvt
bool
OSLCompilerImpl::osl_parse_buffer (const std::string &preprocessed_buffer)
{
// Thread safety with the lexer/parser
static std::mutex oslcompiler_mutex;
std::lock_guard<std::mutex> lock (oslcompiler_mutex);
// N.B. This should only be called if oslcompiler_mutex is held.
ASSERT (oslcompiler == this);
#ifndef OIIO_STRUTIL_HAS_STOF
// Force classic "C" locale for correct '.' decimal parsing.
@@ -395,7 +394,6 @@ OSLCompilerImpl::osl_parse_buffer (const std::string &preprocessed_buffer)
#endif
osl_switch_to_buffer (osl_scan_string (preprocessed_buffer.c_str()));
oslcompiler = this;
oslparse ();
bool parseerr = error_encountered();
osl_delete_buffer (YY_CURRENT_BUFFER);
+96 -51
View File
@@ -94,36 +94,51 @@ TypeSpec
ASTvariable_declaration::typecheck (TypeSpec expected)
{
typecheck_children (m_typespec);
ASTNode* init = this->init().get();
if (! init())
if (! init)
return m_typespec;
const TypeSpec& vt = m_typespec; // Type of the variable
const TypeSpec& et = init->typespec(); // Type of expression assigned
if (m_typespec.is_structure() && ! m_initlist &&
init()->typespec().structure() != m_typespec.structure()) {
et.structure() != vt.structure()) {
// Can't do: struct foo = 1
error ("Cannot initialize structure '%s' with a scalar value",
name().c_str());
error ("Cannot initialize %s %s = %s", type_c_str(vt), name(),
type_c_str(et));
return m_typespec;
}
// If it's a compound initializer, look at the individual pieces
ref init = this->init();
// If it's a compound initializer, the rest of the type checking of the
// individual piece would have already been checked in the child's
// typecheck method.
if (init->nodetype() == compound_initializer_node) {
ASSERT (! init->nextptr() &&
"compound_initializer should be the only initializer");
init = ((ASTcompound_initializer *)init.get())->initlist();
if (init->nextptr())
error ("compound_initializer should be the only initializer");
// init = ((ASTcompound_initializer *)init)->initlist().get();
return m_typespec; // done
}
// Warning to catch confusing comma operator in variable initializers.
// One place this comes up is when somebody forgets the proper syntax
// for constructors, for example
// color x = (a, b, c); // Sets x to (c,c,c)!
// when they really meant
// color x = color(a, b, c);
if (init->nodetype() == comma_operator_node && !typespec().is_closure() &&
(typespec().is_triple() || typespec().is_matrix())) {
warning ("Comma operator is very confusing here. "
"Did you mean to use a constructor: %s = %s(...)?",
m_name.c_str(), typespec().c_str());
// Special case: ok to assign a literal 0 to a closure to
// initialize it.
if (vt.is_closure() && ! et.is_closure() &&
(et.is_float() || et.is_int()) &&
init->nodetype() == literal_node &&
((ASTliteral *)&(*init))->floatval() == 0.0f) {
return m_typespec; // it's ok
}
// Expression must be of a type assignable to the lvalue
if (! assignable (vt, et)) {
// Special case: for int=float, it's just a warning.
if (vt.is_int() && et.is_float())
warning ("Assignment may lose precision: %s %s = %s",
type_c_str(vt), name(), type_c_str(et));
else
error ("Cannot assign %s %s = %s",
type_c_str(vt), name(), type_c_str(et));
return m_typespec;
}
return m_typespec;
@@ -296,8 +311,9 @@ ASTloopmod_statement::typecheck (TypeSpec expected)
TypeSpec
ASTassign_expression::typecheck (TypeSpec expected)
{
TypeSpec vt = var()->typecheck ();
TypeSpec et = expr()->typecheck (vt);
TypeSpec vt = var()->typecheck (); // Type of the variable
TypeSpec et = expr()->typecheck (vt); // Type of the expression assigned
m_typespec = vt;
if (! var()->is_lvalue()) {
error ("Can't assign via %s to something that isn't an lvalue", opname());
@@ -305,21 +321,25 @@ ASTassign_expression::typecheck (TypeSpec expected)
}
ASSERT (m_op == Assign); // all else handled by binary_op
ustring varname;
if (var()->nodetype() == variable_ref_node)
varname = ((ASTvariable_ref*)var().get())->name();
// Handle array case
if (vt.is_array() || et.is_array()) {
if (vt.is_array() && et.is_array() &&
vt.arraylength() >= et.arraylength()) {
if (vt.structure() && (vt.structure() == et.structure())) {
return m_typespec = vt;
return m_typespec;
}
if (equivalent(vt.elementtype(), et.elementtype()) &&
!vt.structure() && !et.structure()) {
return m_typespec = vt;
return m_typespec;
}
}
error ("Cannot assign '%s' to '%s'", type_c_str(et), type_c_str(vt));
return TypeSpec();
error ("Cannot assign %s %s = %s", type_c_str(vt), varname,
type_c_str(et));
return m_typespec;
}
// Special case: ok to assign a literal 0 to a closure to
@@ -328,7 +348,7 @@ ASTassign_expression::typecheck (TypeSpec expected)
(et.is_float() || et.is_int()) &&
expr()->nodetype() == literal_node &&
((ASTliteral *)&(*expr()))->floatval() == 0.0f) {
return TypeSpec(); // it's ok
return m_typespec; // it's ok
}
// If either argument is a structure, they better both be the same
@@ -338,31 +358,24 @@ ASTassign_expression::typecheck (TypeSpec expected)
if (vts == ets)
return m_typespec = vt;
// Otherwise, a structure mismatch
error ("Cannot assign '%s' to '%s'", type_c_str(et), type_c_str(vt));
return TypeSpec();
error ("Cannot assign %s %s = %s", type_c_str(vt), varname,
type_c_str(et));
return m_typespec;
}
// Expression must be of a type assignable to the lvalue
if (! assignable (vt, et)) {
error ("Cannot assign '%s' to '%s'", type_c_str(et), type_c_str(vt));
// FIXME - can we print the variable in question?
return TypeSpec();
// Special case: for int=float, it's just a warning.
if (vt.is_int() && et.is_float())
warning ("Assignment may lose precision: %s %s = %s",
type_c_str(vt), varname, type_c_str(et));
else
error ("Cannot assign %s %s = %s",
type_c_str(vt), varname, type_c_str(et));
return m_typespec;
}
// Warning to catch confusing comma operator in assignment.
// One place this comes up is when somebody forgets the proper syntax
// for constructors, for example
// color x = (a, b, c); // Sets x to (c,c,c)!
// when they really meant
// color x = color(a, b, c);
if (expr()->nodetype() == comma_operator_node && !vt.is_closure() &&
(vt.is_triple() || vt.is_matrix())) {
warning ("Comma operator is very confusing here. "
"Did you mean to use a constructor: = %s(...)?",
vt.c_str());
}
return m_typespec = vt;
return m_typespec;
}
@@ -780,8 +793,14 @@ public:
// Commit infered types of all ASTcompound_initializers scanned.
if (m_success) {
for (auto&& initer : m_adjust) {
std::get<0>(initer)->m_typespec = std::get<1>(initer);
std::get<0>(initer)->m_ctor = std::get<2>(initer);
ASTcompound_initializer* ciptr = std::get<0>(initer);
TypeSpec type = std::get<1>(initer);
// Subtlety: don't reset an already-resolved-known-size
// array to an unlengthed one.
if (! (ciptr->m_typespec.is_sized_array()
&& type.is_unsized_array()))
ciptr->m_typespec = type;
ciptr->m_ctor = std::get<2>(initer);
}
}
}
@@ -816,7 +835,9 @@ public:
// Every element of the array is the same type
TypeSpec elemtype = expected.elementtype();
int nelem = 0;
// Start at 1, as oslc would have already failed in either the case of
// an empty initializer list, or zero-length array.
int nelem = 1;
ASTcompound_initializer* cinit = init;
if (init->initlist()->nodetype() != compound_initializer_node) {
@@ -1948,9 +1969,12 @@ ASTfunction_call::typecheck (TypeSpec expected)
// Instead of typecheck_children, typecheck all arguments except for
// initializer lists, who will be checked against each overload's formal
// specification or each field's known type if is_struct_ctr.
bool any_args_are_compound_initializers = false;
for (ref arg = args(); arg; arg = arg->next()) {
if (arg->nodetype() != compound_initializer_node)
typecheck_list (arg, expected);
else
any_args_are_compound_initializers = true;
}
// Save the currently choosen symbol for error reporting later
@@ -1988,6 +2012,23 @@ ASTfunction_call::typecheck (TypeSpec expected)
}
}
// Fix up actual arguments compound initializiers that were paired with
// user function formal arguments that are unsigned arrays. They were
// not yet typechecked, do so now.
if (any_args_are_compound_initializers && is_user_function()) {
ASTNode* formal = user_function()->formals().get();
for (ASTNode* arg = args().get(); arg && formal;
arg = arg->nextptr(), formal = formal->nextptr()) {
if (arg->nodetype() == compound_initializer_node &&
formal->typespec().is_unsized_array()) {
auto ci_arg = (ASTcompound_initializer*)arg;
TypeSpec expected = formal->typespec();
expected.make_array (listlength(ci_arg->initlist()));
arg->typecheck(expected);
}
}
}
if (m_sym != nullptr) {
if (is_user_function()) {
if (func()->number_of_returns() == 0 &&
@@ -2270,8 +2311,12 @@ OSLCompilerImpl::code_from_type (TypeSpec type) const
out = 's';
else if (elem == TypeDesc::NONE)
out = 'x';
else
ASSERT (0);
else {
out = 'x';
// This only happens in error circumstances. Seems safe to
// return the code for 'void' and hope everything sorts itself
// out with the downstream errors.
}
}
if (type.is_array()) {
-1
View File
@@ -222,7 +222,6 @@ TARGET_LINK_LIBRARIES ( oslexec
${PARTIO_LIBRARIES} ${ZLIB_LIBRARIES}
${Boost_LIBRARIES} ${CMAKE_DL_LIBS}
${CLANG_LIBRARIES}
${LLVM_LIBRARY} ${LLVM_MCJIT_LIBRARY}
${LLVM_LIBRARIES} ${LLVM_LDFLAGS}
${LLVM_SYSTEM_LIBRARIES})
ADD_DEPENDENCIES (oslexec "${CMAKE_SOURCE_DIR}/src/build-scripts/hidesymbols.map")
+4
View File
@@ -396,6 +396,10 @@ LPexp *
Parser::parseModifier(LPexp *e)
{
if (hasInput()) {
if (m_ingroup && (head() == '*' || head() == '{' || head() == '+')) {
m_error = std::string("Repetitions not allowed inside '<...>'");
return NULL;
}
if (head() == '*') {
next();
return new lpexp::Repeat(e);
+5 -1
View File
@@ -539,6 +539,8 @@ ShadingContext::ocio_transform (ustring fromspace, ustring tospace,
tospace != m_last_colorproc_tospace) {
OIIO::ColorConfig& cc (shadingsys().m_colorconfig);
m_last_colorproc = cc.createColorProcessor (fromspace, tospace);
m_last_colorproc_fromspace = fromspace;
m_last_colorproc_tospace = tospace;
}
if (m_last_colorproc)
m_last_colorproc->apply ((float *)&Cout);
@@ -563,13 +565,15 @@ ShadingContext::ocio_transform (ustring fromspace, ustring tospace,
tospace != m_last_colorproc_tospace) {
OIIO::ColorConfig& cc (shadingsys().m_colorconfig);
m_last_colorproc = cc.createColorProcessor (fromspace, tospace);
m_last_colorproc_fromspace = fromspace;
m_last_colorproc_tospace = tospace;
}
if (m_last_colorproc) {
// Use finite differencing to approximate the derivative. Make 3
// color values to convert.
const float eps = 0.001f;
Color3 CC[3] = { C.val(), C.val() + eps*C.dx(), C.val() + eps*C.dy() };
m_last_colorproc->apply ((float *)&CC, 3, 1, 3, sizeof(Color3), 0, 0);
m_last_colorproc->apply ((float *)&CC, 3, 1, 3, sizeof(float), sizeof(Color3), 0);
Cout.set (CC[0],
(CC[1] - CC[0]) * (1.0f / eps),
(CC[2] - CC[0]) * (1.0f / eps));
+20 -18
View File
@@ -1404,6 +1404,7 @@ ShadingSystemImpl::getattribute (ShaderGroup *group, string_view name,
{
if (! group)
return false;
if (name == "groupname" && type == TypeDesc::TypeString) {
*(ustring *)val = group->name();
return true;
@@ -1450,6 +1451,18 @@ ShadingSystemImpl::getattribute (ShaderGroup *group, string_view name,
((ustring *)val)[i] = ustring();
return true;
}
if (name == "group_init_name" && type.basetype == TypeDesc::STRING) {
*(ustring *)val = ustring::format ("group_%d_init", group->id());
return true;
}
if (name == "group_entry_name" && type.basetype == TypeDesc::STRING) {
int nlayers = group->nlayers ();
ShaderInstance *inst = (*group)[nlayers-1];
// This formuation mirrors OSOProcessorBase::layer_function_name()
*(ustring *)val = ustring::format ("%s_%s_%d", group->name(),
inst->layername(), inst->id());
return true;
}
if (name == "num_textures_needed" && type == TypeDesc::TypeInt) {
if (! group->optimized())
optimize_group (*group);
@@ -1606,28 +1619,12 @@ ShadingSystemImpl::getattribute (ShaderGroup *group, string_view name,
*(std::string *)val = exists ? group->m_llvm_ptx_compiled_version : "";
return true;
}
if (name == "group_name" && type.basetype == TypeDesc::PTR) {
*(std::string *)val = group->name().string();
return true;
}
if (name == "group_id" && type == TypeDesc::TypeInt) {
if (! group->optimized())
optimize_group (*group);
*(int *)val = (int) group->id();
return true;
}
if (name == "group_init_name" && type.basetype == TypeDesc::PTR) {
*(std::string *)val = Strutil::format ("group_%d_init", group->id());
return true;
}
if (name == "group_entry_name" && type.basetype == TypeDesc::PTR) {
int nlayers = group->nlayers ();
ShaderInstance *inst = (*group)[nlayers-1];
// This formuation mirrors OSOProcessorBase::layer_function_name()
*(std::string *)val = Strutil::format ("%s_%s_%d", group->name(),
inst->layername(), inst->id());
return true;
}
if (name == "layer_osofiles" && type.basetype == TypeDesc::STRING) {
size_t n = std::min (type.numelements(), (size_t)group->nlayers());
for (size_t i = 0; i < n; ++i)
@@ -2326,7 +2323,7 @@ ShadingSystemImpl::ShaderGroupBegin (string_view groupname,
}
}
string_view paramname (paramname_string);
int lockgeom = true;
int lockgeom = m_lockgeom_default;
// For speed, reserve space. Note that for "unsized" arrays, we only
// preallocate 1 slot and let it grow as needed. That's ok. For
// everything else, we will reserve the right amount up front.
@@ -2515,8 +2512,13 @@ ShadingSystemImpl::ReParameter (ShaderGroup &group, string_view layername_,
int paramindex = layer->findparam (ustring(paramname));
if (paramindex < 0)
return false; // could not find the named parameter
Symbol *sym = layer->symbol (paramindex);
ASSERT (sym != NULL);
if (!sym) {
// Can have a paramindex >= 0, but no symbol when it's a master-symbol
DASSERT(layer->mastersymbol(paramindex) && "No symbol for paramindex");
return false;
}
// Check for mismatch versus previously-declared type
if (!equivalent(sym->typespec(), type))
+6 -4
View File
@@ -178,22 +178,24 @@ void spline_inverse (const SplineBasis *spline,
int knot_arraylen)
{
// account for out-of-range inputs, just clamp to the values we have
int lowindex = spline->basis_step == 1 ? 1 : 0;
int highindex = spline->basis_step == 1 ? knot_count-2 : knot_count-1;
bool increasing = knots[1] < knots[knot_count-2];
if (increasing) {
if (y <= knots[1]) {
if (y <= knots[lowindex]) {
x = YTYPE(0);
return;
}
if (y >= knots[knot_count-2]) {
if (y >= knots[highindex]) {
x = YTYPE(1);
return;
}
} else {
if (y >= knots[1]) {
if (y >= knots[lowindex]) {
x = YTYPE(0);
return;
}
if (y <= knots[knot_count-2]) {
if (y <= knots[highindex]) {
x = YTYPE(1);
return;
}
+1 -1
View File
@@ -61,7 +61,7 @@ macro (mx_oslc_compile)
get_filename_component(mxfile_justname ${mxfile} NAME)
get_filename_component(oslfile_justname ${oslfile} NAME)
get_filename_component(osofile_justname ${osofile} NAME)
message (STATUS "oslc will make ${mxfile_justname} -> ${oslfile_justname} -> ${osofile_justname}")
# message (STATUS "oslc will make ${mxfile_justname} -> ${oslfile_justname} -> ${osofile_justname}")
endif ()
add_custom_command (OUTPUT ${osofile}
COMMAND python "${CMAKE_CURRENT_SOURCE_DIR}/build_materialX_osl.py"
+33 -8
View File
@@ -343,17 +343,17 @@ normal step (normal edge, normal x) BUILTIN;
float step (float edge, float x) BUILTIN;
float smoothstep (float edge0, float edge1, float x) BUILTIN;
color smoothstep (color edge0, color edge1, color in)
color smoothstep (color edge0, color edge1, color x)
{
return color (smoothstep(edge0[0], edge1[0], in[0]),
smoothstep(edge0[1], edge1[1], in[1]),
smoothstep(edge0[2], edge1[2], in[2]));
return color (smoothstep(edge0[0], edge1[0], x[0]),
smoothstep(edge0[1], edge1[1], x[1]),
smoothstep(edge0[2], edge1[2], x[2]));
}
vector smoothstep (vector edge0, vector edge1, vector in)
vector smoothstep (vector edge0, vector edge1, vector x)
{
return vector (smoothstep(edge0[0], edge1[0], in[0]),
smoothstep(edge0[1], edge1[1], in[1]),
smoothstep(edge0[2], edge1[2], in[2]));
return vector (smoothstep(edge0[0], edge1[0], x[0]),
smoothstep(edge0[1], edge1[1], x[1]),
smoothstep(edge0[2], edge1[2], x[2]));
}
float linearstep (float edge0, float edge1, float x) {
@@ -366,6 +366,18 @@ float linearstep (float edge0, float edge1, float x) {
}
return result;
}
color linearstep (color edge0, color edge1, color x)
{
return color (linearstep(edge0[0], edge1[0], x[0]),
linearstep(edge0[1], edge1[1], x[1]),
linearstep(edge0[2], edge1[2], x[2]));
}
vector linearstep (vector edge0, vector edge1, vector x)
{
return vector (linearstep(edge0[0], edge1[0], x[0]),
linearstep(edge0[1], edge1[1], x[1]),
linearstep(edge0[2], edge1[2], x[2]));
}
float smooth_linearstep (float edge0, float edge1, float x_, float eps_) {
float result;
@@ -385,6 +397,19 @@ float smooth_linearstep (float edge0, float edge1, float x_, float eps_) {
return result;
}
color smooth_linearstep (color edge0, color edge1, color x, color eps)
{
return color (smooth_linearstep(edge0[0], edge1[0], x[0], eps[0]),
smooth_linearstep(edge0[1], edge1[1], x[1], eps[1]),
smooth_linearstep(edge0[2], edge1[2], x[2], eps[2]));
}
vector smooth_linearstep (vector edge0, vector edge1, vector x, vector eps)
{
return vector (smooth_linearstep(edge0[0], edge1[0], x[0], eps[0]),
smooth_linearstep(edge0[1], edge1[1], x[1], eps[1]),
smooth_linearstep(edge0[2], edge1[2], x[2], eps[2]));
}
float aastep (float edge, float s, float dedge, float ds) {
// Box filtered AA step
float width = fabs(dedge) + fabs(ds);
+3 -4
View File
@@ -481,10 +481,9 @@ void make_optix_materials ()
shadingsys->optimize_group (groupref.get());
std::string group_name, init_name, entry_name;
shadingsys->getattribute (groupref.get(), "group_name", OSL::TypeDesc::PTR, &group_name);
shadingsys->getattribute (groupref.get(), "group_init_name", OSL::TypeDesc::PTR, &init_name);
shadingsys->getattribute (groupref.get(), "group_entry_name", OSL::TypeDesc::PTR, &entry_name);
shadingsys->getattribute (groupref.get(), "groupname", group_name);
shadingsys->getattribute (groupref.get(), "group_init_name", init_name);
shadingsys->getattribute (groupref.get(), "group_entry_name", entry_name);
// Retrieve the compiled ShaderGroup PTX
std::string osl_ptx;
+26 -3
View File
@@ -999,11 +999,16 @@ test_shade (int argc, const char *argv[])
{
OIIO::Timer timer;
// Request a TextureSystem (by default it will be the global shared
// one). This isn't strictly necessary, if you pass nullptr to
// ShadingSystem ctr, it will ask for the shared one internally.
TextureSystem *texturesys = TextureSystem::create();
// Create a new shading system. We pass it the RendererServices
// object that services callbacks from the shading system, NULL for
// the TextureSystem (that just makes 'create' make its own TS), and
// an error handler.
shadingsys = new ShadingSystem (&rend, NULL, &errhandler);
shadingsys = new ShadingSystem (&rend, texturesys, &errhandler);
// Register the layout of all closures known to this renderer
// Any closure used by the shader which is not registered, or
@@ -1239,7 +1244,25 @@ test_shade (int argc, const char *argv[])
// We're done with the shading system now, destroy it
shadergroup.reset (); // Must release this before destroying shadingsys
delete shadingsys;
return EXIT_SUCCESS;
delete shadingsys;
int retcode = EXIT_SUCCESS;
#if OPENIMAGEIO_VERSION >= 10904
// Double check that there were no uncaught errors in the texture
// system and image cache.
std::string err = texturesys->geterror();
if (!err.empty()) {
std::cout << "ERRORS left in TextureSystem:\n" << err << "\n";
retcode = EXIT_FAILURE;
}
OIIO::ImageCache *ic = texturesys->imagecache();
err = ic ? ic->geterror() : std::string();
if (!err.empty()) {
std::cout << "ERRORS left in ImageCache:\n" << err << "\n";
retcode = EXIT_FAILURE;
}
#endif
return retcode;
}
+3
View File
@@ -43,3 +43,6 @@ start of outer, j=3
i = 3
i = 4
Testing break in an infinite for loop:
worked
+6
View File
@@ -31,5 +31,11 @@ shader test ()
break;
}
printf ("\nTesting break in an infinite for loop:\n");
for ( ; ; ) {
break;
// N.B. This used to crash oslc, if this compiles, it's fine.
}
printf ("worked\n");
}
+2
View File
@@ -40,4 +40,6 @@ ac[1] = {(6 7 8 5)}
ac[2] = {(23 33 43 22)}
ac[3] = {(1 6 1 1)}
AC: ({11 12 13})
passed array[3] = {1, 2, 3}
passed array[] = {1, 2, 3}
+17
View File
@@ -54,6 +54,19 @@ bcolor colorvalue() {
return { {6,7,8}, 5 };
}
void receive_array_3 (float array[3]) {
printf ("passed array[3] = {%g, %g, %g}\n",
array[0], array[1], array[2]);
}
void receive_array_any (float array[]) {
printf ("passed array[] = {");
for (int i = 0; i < arraylength(array); ++i)
printf ("%s%g", i ? ", " : "", array[i]);
printf ("}\n");
}
shader test( // FIXME: custcolor4 cina[2] = {{color(1),1}, {color(1),1}},
vector vin = { 1, 2, 3 },
@@ -127,4 +140,8 @@ shader test( // FIXME: custcolor4 cina[2] = {{color(1),1}, {color(1),1}},
acolor cc = acolorcopy({10, {11,12,13}});
printf("AC: ({%g})\n", cc.rgb);
// Test passing init list for fixed-length and un-lengthed array params
receive_array_3 ({1.0, 2.0, 3.0});
receive_array_any ({1.0, 2.0, 3.0});
}
Binary file not shown.
+17 -5
View File
@@ -2,15 +2,27 @@ shader
test (output color Cout = 0)
{
Cout = 0;
if (v < 0.2) // degenerate linearstep with coincident edges
if (v < 0.1) // degenerate linearstep with coincident edges
Cout = linearstep (0.5, 0.5, u);
else if (v < 0.4) // ordinary linearstep
else if (v < 0.2) // ordinary linearstep
Cout = linearstep (0.25, 0.75, u);
else if (v < 0.6) // deginerate sls with eps==0
else if (v < 0.3) // degenerate sls with eps==0
Cout = smooth_linearstep (0.25, 0.75, u, 0.0);
else if (v < 0.8) // regular sls
else if (v < 0.4) // regular sls
Cout = smooth_linearstep (0.25, 0.75, u, 0.05);
else if (v < 1.0) // degenerate sls with coincident edges
else if (v < 0.5) // degenerate sls with coincident edges
Cout = smooth_linearstep (0.5, 0.5, u, 0.0);
else if (v < 0.6) // degenerate linearstep with coincident edges
Cout = linearstep (color(0.5), color(0.5), u);
else if (v < 0.7) // ordinary linearstep
Cout = linearstep (color(0.25), color(0.75), u);
else if (v < 0.8) // degenerate sls with eps==0
Cout = smooth_linearstep (color(0.25), color(0.75), u, color(0.0));
else if (v < 0.9) // regular sls
Cout = smooth_linearstep (color(0.25), color(0.75), u, color(0.05));
else if (v <= 1.0) // degenerate sls with coincident edges
Cout = smooth_linearstep (color(0.5), color(0.5), u, color(0.0));
Cout = 0.1 + Cout * 0.8;
}
+74 -58
View File
@@ -65,64 +65,9 @@ Varying do...while(i<5):
i = 4.5
After loop, i = 5.5
Count 0 to 4 using 'while':
i = 0
i = 1
i = 2
i = 3
i = 4
After loop, i = 5
Varying 'while', count up until < 5:
Start with i = 1.5
iteration:
i = 1.5
iteration:
i = 2.5
iteration:
i = 3.5
iteration:
i = 4.5
After loop, i = 5.5
Count 0 to 4 using 'for':
i = 0
i = 1
i = 2
i = 3
i = 4
Varying 'for', count up until < 5:
outer scope i = 15
iteration:
i = 1.5
iteration:
i = 2.5
iteration:
i = 3.5
iteration:
i = 4.5
outer scope i = 15
Count using 'do...while(i<5)':
i = 0
i = 1
i = 2
i = 3
i = 4
After loop, i = 5
Varying do...while(i<5):
Start with i = 1.5
iteration:
i = 1.5
iteration:
i = 2.5
iteration:
i = 3.5
iteration:
i = 4.5
After loop, i = 5.5
Testing while(var) hit=1
first loop, i=0, hit=1
loop exited, hit is 0
Count 0 to 4 using 'while':
i = 0
@@ -183,6 +128,73 @@ Varying do...while(i<5):
i = 4.5
After loop, i = 5.5
Testing while(var) hit=1
first loop, i=0, hit=1
loop exited, hit is 0
Count 0 to 4 using 'while':
i = 0
i = 1
i = 2
i = 3
i = 4
After loop, i = 5
Varying 'while', count up until < 5:
Start with i = 1.5
iteration:
i = 1.5
iteration:
i = 2.5
iteration:
i = 3.5
iteration:
i = 4.5
After loop, i = 5.5
Count 0 to 4 using 'for':
i = 0
i = 1
i = 2
i = 3
i = 4
Varying 'for', count up until < 5:
outer scope i = 15
iteration:
i = 1.5
iteration:
i = 2.5
iteration:
i = 3.5
iteration:
i = 4.5
outer scope i = 15
Count using 'do...while(i<5)':
i = 0
i = 1
i = 2
i = 3
i = 4
After loop, i = 5
Varying do...while(i<5):
Start with i = 1.5
iteration:
i = 1.5
iteration:
i = 2.5
iteration:
i = 3.5
iteration:
i = 4.5
After loop, i = 5.5
Testing while(var) hit=1
first loop, i=0, hit=1
loop exited, hit is 0
Count 0 to 4 using 'while':
i = 0
i = 1
@@ -236,3 +248,7 @@ Varying do...while(i<5):
i = 4.5
After loop, i = 5.5
Testing while(var) hit=1
first loop, i=0, hit=1
loop exited, hit is 0
+15 -1
View File
@@ -64,5 +64,19 @@ test ()
}
// FIXME -- try break/continue
// Regression test -- codegen problem made this an infinite loop, a
// problem when an int variable was directly used instead of a
// comparison.
{
int hit=1;
int i = 0;
printf ("\nTesting while(var) hit=%d\n", hit);
while (hit) {
printf (" first loop, i=%d, hit=%d\n", i, hit);
hit = 0;
++i;
}
printf (" loop exited, hit is %d\n", hit);
}
}
+1
View File
@@ -19,6 +19,7 @@ shader comma ()
printf ("Lo = %d, hi = %d (expect: 0,1)\n", lo, hi);
// Test the return value of a commma expression
// Note: this will make a warning, because it's stupid.
float x = 3.14;
int y = 5;
int z = (x, y);
+1
View File
@@ -1,3 +1,4 @@
comma.osl:25: warning: Comma operator inside parenthesis is probably an error -- it is not a vector/color.
Compiled comma.osl -> comma.oso
for loop: amp = 0.03125, freq = 16, sum = 0
Lo = 0, hi = 1 (expect: 0,1)
@@ -0,0 +1,6 @@
test.osl:17: warning: Assignment may lose precision: int i = float
test.osl:18: warning: Assignment may lose precision: int i = float
test.osl:26: error: Cannot assign closure color cc = int
test.osl:32: error: Cannot initialize struct vector4 v4 = struct vector2
test.osl:34: error: Cannot assign struct vector2 v2 = struct vector4
FAILED test.osl
+5
View File
@@ -0,0 +1,5 @@
#!/usr/bin/env python
# command = oslc("test.osl")
# don't even need that -- it's automatic
failureok = 1 # this test is expected to have oslc errors
@@ -0,0 +1,36 @@
// Test a variety of scenarios that should report type errors related to
// assignments. We need to test both simple assignment as well as variable
// declaration with initialization assignment, since they are different
// grammatical constructs.
#include "vector2.h"
#include "vector4.h"
shader
test()
{
// Assigning float to int is not allowed without a cast
{
float f = M_PI;
int i = f; // error
i = f; // error
i = (int)f; // ok
}
// Assigning scalar to closure, unless the scalar is 0
{
closure color cc = 0; // ok
cc = 0; // ok
cc = 1; // error
}
// Assigning structs
{
vector2 v2 = {0.0}; // ok
vector4 v4 = v2; // error -- incompatible structs
v4 = v4; // ok
v2 = v4; // error -- incompatible structs
}
}
+1 -1
View File
@@ -1,3 +1,3 @@
test.osl:6: error: Not allowed: 'closure color * closure color'
test.osl:6: error: Cannot assign 'unknown' to 'closure color'
test.osl:6: error: Cannot assign closure color Ci = unknown
FAILED test.osl
+7
View File
@@ -0,0 +1,7 @@
test.osl:7: error: Too many initializers for a 'struct athing[3]'
test.osl:10: error: Too many initializers for a 'float[4]'
test.osl:12: error: Too many initializers for a 'float[1]'
test.osl:15: error: Too many initializers for a 'float[5]'
test.osl:17: error: Invalid array length (0)
test.osl:17: error: Invalid array length for toalfail
test.osl:18: error: Syntax error: syntax error
+6
View File
@@ -0,0 +1,6 @@
#!/usr/bin/env python
# command = oslc("test.osl")
# don't even need that -- it's automatic
failureok = 1 # this test is expected to have oslc errors
+19
View File
@@ -0,0 +1,19 @@
struct athing { float a, b; };
struct anestedthing { float a, b; float c[5]; };
shader test() {
athing goodthing[4] = { {0,1}, {1,2}, {3,4}, {5,6} };
athing badthing[3] = { {0,1}, {1,2}, {3,4}, {5,6} };
float good[4] = { 0 ? 0 : 0, 1, 2, 3 };
float bad[4] = { 0, 1, 2, 3 ? 3 : 3, 4 };
float badone[1] = { 1, 2 };
anestedthing oknest = { 1, 2, {1,2,3,4,5} };
anestedthing badnest = { 1, 2, {1,2,3,4,5,6} };
int toalfail[0];
int oncemore[1] = {};
}
+1 -1
View File
@@ -1,2 +1,2 @@
test.osl:2: error: shader parameter 'a' MUST have a default initializer
test.osl:2: error: shader parameter 'a' requires a default initializer
FAILED test.osl
+1 -1
View File
@@ -1,4 +1,4 @@
test.osl:10: error: Cannot initialize structure 'A' with a scalar value
test.osl:10: error: Cannot initialize struct rgba A = int
test.osl:13: error: Constructor for 'rgba' has the wrong number of arguments (expected 2, got 1)
test.osl:16: error: Constructor for 'rgba' has the wrong number of arguments (expected 2, got 3)
test.osl:16: error: Too many initializers for struct 'rgba'
@@ -0,0 +1,4 @@
test.osl:4: error: Unknown struct name: mat2
test.osl:6: error: function 'mat2' was not declared in this scope
test.osl:6: error: No matching function call to 'mat2 (float, float, float, float)'
FAILED test.osl
+5
View File
@@ -0,0 +1,5 @@
#!/usr/bin/env python
# command = oslc("test.osl")
# don't even need that -- it's automatic
failureok = 1 # this test is expected to have oslc errors
+12
View File
@@ -0,0 +1,12 @@
// No mat2 is known. This used to hit an assertion.
// Correct behavior is understandable error message(s).
mat2 rotmat(float a)
{
return mat2(cos(a),sin(a),-sin(a),cos(a));
}
shader test ()
{
printf ("Did not crash\n");
}
@@ -1,6 +1,6 @@
test.osl:4: error: cannot write to "x" (read-only symbol)
test.osl:5: error: cannot write to "x" (read-only symbol)
test.osl:6: error: cannot write to "i" (read-only symbol)
test.osl:7: error: cannot write to "i" (read-only symbol)
test.osl:20: error: cannot write to "u" (read-only symbol)
test.osl:4: error: cannot write to non-output parameter "x"
test.osl:5: error: cannot write to non-output parameter "x"
test.osl:6: error: cannot write to non-output parameter "i"
test.osl:7: error: cannot write to non-output parameter "i"
test.osl:20: error: cannot write to non-output parameter "u"
FAILED test.osl
+3 -2
View File
@@ -1,3 +1,4 @@
test.osl:3: warning: Comma operator is very confusing here. Did you mean to use a constructor: x = vector(...)?
test.osl:4: warning: Comma operator is very confusing here. Did you mean to use a constructor: = color(...)?
test.osl:3: warning: Comma operator inside parenthesis is probably an error -- it is not a vector/color.
test.osl:4: warning: Comma operator inside parenthesis is probably an error -- it is not a vector/color.
test.osl:5: warning: Comma operator inside parenthesis is probably an error -- it is not a vector/color.
Compiled test.osl -> test.oso
+1
View File
@@ -2,4 +2,5 @@ shader test ( output color Cout = 0 )
{
vector x = (1, 2, 3);
Cout = (u, v, 0);
Cout *= (0, 1, 2);
}
Binary file not shown.
@@ -0,0 +1,3 @@
Compiled test.osl -> test.oso
Output Cout to out.tif
+5
View File
@@ -0,0 +1,5 @@
#!/usr/bin/env python
command += testshade("-g 256 256 -d uint8 -o Cout out.tif test")
outputs = [ "out.txt", "out.tif" ]
+26
View File
@@ -0,0 +1,26 @@
shader test (output color Cout = 0)
{
int spltype = int(clamp(v*4,0,3));
string basis[4] = { "linear", "catmull-rom", "bspline", "bezier" };
float cvsbezier[4] = { 0, 1.0/3, 2.0/3, 1 };
float cvslinear[4] = { -1, 0, 1, 2};
float vv = fmod (v*4, 1.0);
if (vv < 0.1 || vv > 0.9) {
Cout = 0.0;
} else {
float s, is, invs;
if (basis[spltype] == "bezier") {
s = spline(basis[spltype], u, cvsbezier);
is = splineinverse(basis[spltype], u, cvsbezier);
invs = splineinverse(basis[spltype], s, cvsbezier);
} else {
s = spline(basis[spltype], u, cvslinear);
is = splineinverse(basis[spltype], u, cvslinear);
invs = splineinverse(basis[spltype], s, cvslinear);
}
Cout = vv < 0.5 ? s : is;
// Color red if splineinverse(spline(u)) != u
if (abs(s-invs) > 0.001)
Cout[0] = abs(s-invs);
}
}
+3 -3
View File
@@ -1,4 +1,4 @@
test.osl:29: error: Cannot assign 'struct Bstruct' to 'struct Astruct'
test.osl:32: error: Cannot assign 'int' to 'struct Bstruct'
test.osl:35: error: Cannot initialize structure 'c' with a scalar value
test.osl:29: error: Cannot assign struct Astruct a = struct Bstruct
test.osl:32: error: Cannot assign struct Bstruct b = int
test.osl:35: error: Cannot initialize struct Astruct c = int
FAILED test.osl
+4 -4
View File
@@ -26,7 +26,7 @@ XYZ 0.090 0.036 0.475 = rgb 0.000 0.000 0.500
transformc ("linear","sRGB",(0.500 1.000 0.000)) = 0.735 1.000 0.000
transformc ("sRGB","linear",(0.500 1.000 0.000)) = 0.214 1.000 0.000
transformc ("rgb","YIQ",(0.000 0.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.057 -0.161 0.155 / 0.299 0.596 0.212 / 0.587 -0.275 -0.523
transformc ("rgb","sRGB",(0.000 0.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.000 0.000 0.500 / 12.920 0.000 0.000 / 0.000 1.000 0.000
transformc ("rgb","sRGB",(0.000 0.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.000 0.000 0.735 / 12.920 0.000 0.000 / 0.000 12.920 0.000
rgb 0.500 1.000 0.000 = hsv 0.250 1.000 1.000
hsv 0.250 1.000 1.000 = rgb 0.500 1.000 0.000
@@ -55,7 +55,7 @@ XYZ 0.502 0.249 0.494 = rgb 1.000 -0.000 0.500
transformc ("linear","sRGB",(0.500 1.000 0.000)) = 0.735 1.000 0.000
transformc ("sRGB","linear",(0.500 1.000 0.000)) = 0.214 1.000 0.000
transformc ("rgb","YIQ",(1.000 0.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.356 0.436 0.368 / 0.299 0.596 0.212 / 0.587 -0.275 -0.523
transformc ("rgb","sRGB",(1.000 0.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 1.000 0.000 0.500 / 0.440 0.000 0.000 / 0.000 1.000 0.000
transformc ("rgb","sRGB",(1.000 0.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 1.000 0.000 0.735 / 0.440 0.000 0.000 / 0.000 12.920 0.000
rgb 0.500 1.000 0.000 = hsv 0.250 1.000 1.000
hsv 0.250 1.000 1.000 = rgb 0.500 1.000 0.000
@@ -84,7 +84,7 @@ XYZ 0.448 0.751 0.594 = rgb -0.000 1.000 0.500
transformc ("linear","sRGB",(0.500 1.000 0.000)) = 0.735 1.000 0.000
transformc ("sRGB","linear",(0.500 1.000 0.000)) = 0.214 1.000 0.000
transformc ("rgb","YIQ",(0.000 1.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.644 -0.436 -0.368 / 0.299 0.596 0.212 / 0.587 -0.275 -0.523
transformc ("rgb","sRGB",(0.000 1.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.000 1.000 0.500 / 12.920 0.000 0.000 / 0.000 1.000 0.000
transformc ("rgb","sRGB",(0.000 1.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.000 1.000 0.735 / 12.920 0.000 0.000 / 0.000 0.440 0.000
rgb 0.500 1.000 0.000 = hsv 0.250 1.000 1.000
hsv 0.250 1.000 1.000 = rgb 0.500 1.000 0.000
@@ -113,6 +113,6 @@ XYZ 0.860 0.964 0.613 = rgb 1.000 1.000 0.500
transformc ("linear","sRGB",(0.500 1.000 0.000)) = 0.735 1.000 0.000
transformc ("sRGB","linear",(0.500 1.000 0.000)) = 0.214 1.000 0.000
transformc ("rgb","YIQ",(1.000 1.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 0.943 0.161 -0.155 / 0.299 0.596 0.212 / 0.587 -0.275 -0.523
transformc ("rgb","sRGB",(1.000 1.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 1.000 1.000 0.500 / 0.440 0.000 0.000 / 0.000 1.000 0.000
transformc ("rgb","sRGB",(1.000 1.000 0.500 / 1.000 0.000 0.000 / 0.000 1.000 0.000)) = 1.000 1.000 0.735 / 0.440 0.000 0.000 / 0.000 0.440 0.000