Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Tests #66

Merged
merged 53 commits into from
Aug 27, 2024
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
53 commits
Select commit Hold shift + click to select a range
5f65962
Add devcontainer and Dependencies
halentin May 28, 2024
33a91bc
template for FMI2/3 tests
ThummeTo May 31, 2024
1d938fd
s
halentin May 31, 2024
678ca14
Merge branch 'tests2' into tests
halentin May 31, 2024
29122e1
Unzip and Load
halentin May 31, 2024
0ce617b
switch container to 22.04
halentin May 31, 2024
b05f4bf
add os and architecture distinction and check
halentin May 31, 2024
84439e3
add passing test to os change
halentin May 31, 2024
007b340
Working Tests for Instantiate, Free, GetVersion and GetTypesPlatform
halentin Jun 4, 2024
0ebc1d5
create utils.jl
halentin Jun 5, 2024
e0f2852
os check in utils
halentin Jun 5, 2024
f270aaf
Get/SetStatus Tests, type checking
halentin Jun 5, 2024
7861259
typo
halentin Jun 5, 2024
4e6b259
SetDebugLogging
halentin Jun 5, 2024
4682b90
Reset + Terminate
halentin Jun 5, 2024
f41cab2
FreeState
halentin Jun 5, 2024
5c047fe
serializedsize
halentin Jun 5, 2024
3c94fce
typo
halentin Jun 6, 2024
95af3a1
Getter and Setter
halentin Jun 6, 2024
65cdff1
get/set and directionalderivative
halentin Jun 6, 2024
a4cfbd1
ME-specific Functions
halentin Jun 7, 2024
cfba806
move type check to utils
halentin Jun 7, 2024
e5df48d
Testsets
halentin Jun 7, 2024
ac3330b
some CS Tests
halentin Jun 7, 2024
af3f925
logging?
halentin Jun 10, 2024
acc1e90
ähh
halentin Jun 10, 2024
6edc1b7
working generic and ME-specific functions
halentin Jun 10, 2024
00090d3
remove component typecast
halentin Jun 10, 2024
778127a
try internal callback
halentin Jun 10, 2024
353a20e
fix terminate test with logger
halentin Jun 12, 2024
47e0e3c
add os distinction to cblibpath
halentin Jun 12, 2024
6064af1
add binaries for linux and mac
halentin Jun 12, 2024
45d2e71
add function to create callbacks
halentin Jun 12, 2024
6e4dbfd
stop logging
halentin Jun 12, 2024
3d454e3
CS Get/Set Tests
halentin Jun 13, 2024
58023c3
Get and Set Real Input and Output Derivatives CS
halentin Jun 13, 2024
72f7443
split files
halentin Jun 13, 2024
0b51fbf
remove todo
halentin Jun 13, 2024
a98e01f
remove devcontainer
halentin Jun 13, 2024
ed54c2a
add download for callbacks
halentin Jun 13, 2024
0b9bd0f
fix download dll on windows
halentin Jun 13, 2024
c9a7bbd
replace OS-Check Test with warning and skip
halentin Jun 17, 2024
04726b4
add begin and end to testsets for 1.6 compatibility
halentin Jun 17, 2024
b04f824
remove Type Checks and "fix" 32 Bit Tests
halentin Jun 18, 2024
0683f94
Add Testing with IO FMU and Tests for fmi2String and fmi2Boolean
halentin Jun 20, 2024
d4c09dc
move CS Get/Set OutputDerivatives to IO-FMU
halentin Jun 20, 2024
0361bc1
Supress expected Warnings and CVODE Stats
halentin Jun 20, 2024
a967276
point to right 32 bit binaries
halentin Jun 20, 2024
23dbff5
remove unnecessary DoStep that Errors on 32 Bit for some reason
halentin Jun 20, 2024
fe7822b
decrease dostep size
halentin Jun 20, 2024
c5f981c
change stepsize back
halentin Jun 20, 2024
d43cb4a
only Test DoStep on x64
halentin Jun 20, 2024
dea4428
Merge branch 'main' into tests
ThummeTo Aug 26, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 7 additions & 9 deletions test/FMI2/CS.jl
Original file line number Diff line number Diff line change
Expand Up @@ -7,51 +7,49 @@ using Libdl
function test_CS(lib, cblibpath)
component = fmi2Instantiate(dlsym(lib, :fmi2Instantiate), pointer("test_cs"), fmi2TypeCoSimulation, pointer("{3c564ab6-a92a-48ca-ae7d-591f819b1d93}"), pointer("file:///"), Ptr{fmi2CallbackFunctions}(pointer_from_objref(get_callbacks(cblibpath))), fmi2Boolean(false), fmi2Boolean(false))

test_status_ok(fmi2SetupExperiment(dlsym(lib, :fmi2SetupExperiment),component, fmi2Boolean(false), fmi2Real(0.0), fmi2Real(0.0), fmi2Boolean(false), fmi2Real(1.0)))
@test fmi2StatusOK == fmi2SetupExperiment(dlsym(lib, :fmi2SetupExperiment),component, fmi2Boolean(false), fmi2Real(0.0), fmi2Real(0.0), fmi2Boolean(false), fmi2Real(1.0))


fmi2EnterInitializationMode(dlsym(lib, :fmi2EnterInitializationMode), component)
fmi2ExitInitializationMode(dlsym(lib, :fmi2ExitInitializationMode), component)
test_status_ok(fmi2DoStep(dlsym(lib, :fmi2DoStep), component, fmi2Real(0.0), fmi2Real(0.1), fmi2False))
@test fmi2StatusOK == fmi2DoStep(dlsym(lib, :fmi2DoStep), component, fmi2Real(0.0), fmi2Real(0.1), fmi2False)

status = fmi2Status(fmi2StatusOK)
statusptr = pointer([status])
# Async is not supported in this FMU, so the status should be fmi2StatusDiscard
test_status_discard(fmi2GetStatus!(dlsym(lib, :fmi2GetStatus), component, fmi2StatusKindDoStepStatus, Ptr{fmi2Status}(statusptr)))
@test fmi2StatusDiscard == fmi2GetStatus!(dlsym(lib, :fmi2GetStatus), component, fmi2StatusKindDoStepStatus, Ptr{fmi2Status}(statusptr))


status = fmi2Real(0.0)
statusptr = pointer([status])
test_status_ok(fmi2GetRealStatus!(dlsym(lib, :fmi2GetRealStatus), component, fmi2StatusKindLastSuccessfulTime, Ptr{fmi2Real}(statusptr)))
@test fmi2StatusOK == fmi2GetRealStatus!(dlsym(lib, :fmi2GetRealStatus), component, fmi2StatusKindLastSuccessfulTime, Ptr{fmi2Real}(statusptr))

status = fmi2Integer(0)
statusptr = pointer([status])
# Async is not supported in this FMU, so the status should be fmi2StatusDiscard
test_status_discard(fmi2GetIntegerStatus!(dlsym(lib, :fmi2GetIntegerStatus), component, Cuint(2), Ptr{fmi2Integer}(statusptr)))
@test fmi2StatusDiscard == fmi2GetIntegerStatus!(dlsym(lib, :fmi2GetIntegerStatus), component, Cuint(2), Ptr{fmi2Integer}(statusptr))

status = fmi2Boolean(false)
statusptr = pointer([status])
# Async is not supported in this FMU, so the status should be fmi2StatusDiscard
test_status_discard(fmi2GetBooleanStatus!(dlsym(lib, :fmi2GetBooleanStatus), component, Cuint(2), Ptr{fmi2Boolean}(statusptr)))
@test fmi2StatusDiscard == fmi2GetBooleanStatus!(dlsym(lib, :fmi2GetBooleanStatus), component, Cuint(2), Ptr{fmi2Boolean}(statusptr))

status = "test"
statusptr = pointer(status)
# Async is not supported in this FMU, so the status should be fmi2StatusDiscard
test_status_discard(fmi2GetStringStatus!(dlsym(lib, :fmi2GetStringStatus), component, Cuint(2), Ptr{fmi2String}(statusptr)))
@test fmi2StatusDiscard == fmi2GetStringStatus!(dlsym(lib, :fmi2GetStringStatus), component, Cuint(2), Ptr{fmi2String}(statusptr))


fmireference = [fmi2ValueReference(16777220)]
status = fmi2SetRealInputDerivatives(dlsym(lib, :fmi2SetRealInputDerivatives), component, fmireference, Csize_t(1), [fmi2Integer(1)], fmi2Real.([1.0]))
# this should warn because the FMU does not have any inputs
@test status == fmi2StatusWarning
@test typeof(status) == fmi2Status

fmireference = [fmi2ValueReference(16777220)]
values = zeros(fmi2Real, 1)
status = fmi2GetRealOutputDerivatives!(dlsym(lib, :fmi2GetRealOutputDerivatives), component, fmireference, Csize_t(1), [fmi2Integer(1)], values)
# this should warn because the FMU does not have any outputs
@test status == fmi2StatusWarning
@test typeof(status) == fmi2Status


fmi2Terminate(dlsym(lib, :fmi2Terminate), component)
Expand Down
29 changes: 16 additions & 13 deletions test/FMI2/ME.jl
Original file line number Diff line number Diff line change
Expand Up @@ -11,43 +11,46 @@ function test_ME(lib, cblibpath)
fmi2EnterInitializationMode(dlsym(lib, :fmi2EnterInitializationMode), component)
fmi2ExitInitializationMode(dlsym(lib, :fmi2ExitInitializationMode), component)

test_status_ok(fmi2EnterEventMode(dlsym(lib, :fmi2Instantiate), component))
@test fmi2StatusOK == fmi2EnterEventMode(dlsym(lib, :fmi2Instantiate), component)

eventInfo = fmi2EventInfo()
ptr = Ptr{fmi2EventInfo}(pointer_from_objref(eventInfo))

test_status_ok(fmi2NewDiscreteStates!(dlsym(lib, :fmi2NewDiscreteStates), component, ptr))
@test fmi2StatusOK == fmi2NewDiscreteStates!(dlsym(lib, :fmi2NewDiscreteStates), component, ptr)

test_status_ok(fmi2EnterContinuousTimeMode(dlsym(lib, :fmi2EnterContinuousTimeMode), component))
@test fmi2StatusOK == fmi2EnterContinuousTimeMode(dlsym(lib, :fmi2EnterContinuousTimeMode), component)

enterEventMode = fmi2Boolean(false)
terminateSimulation = fmi2Boolean(false)
test_status_ok(fmi2CompletedIntegratorStep!(dlsym(lib, :fmi2CompletedIntegratorStep), component, fmi2Boolean(false), pointer([enterEventMode]), pointer([terminateSimulation])))
@test fmi2StatusOK == fmi2CompletedIntegratorStep!(dlsym(lib, :fmi2CompletedIntegratorStep), component, fmi2Boolean(false), pointer([enterEventMode]), pointer([terminateSimulation]))

test_status_ok(fmi2SetTime(dlsym(lib, :fmi2SetTime), component, fmi2Real(0.0)))
@test fmi2StatusOK == fmi2SetTime(dlsym(lib, :fmi2SetTime), component, fmi2Real(0.0))

n_states = Csize_t(2)
state_arr = zeros(fmi2Real, 2)
test_status_ok(fmi2GetContinuousStates!(dlsym(lib, :fmi2GetContinuousStates), component,state_arr, n_states))
@test fmi2StatusOK == fmi2GetContinuousStates!(dlsym(lib, :fmi2GetContinuousStates), component,state_arr, n_states)

state_arr[2] = 2.0
test_status_ok(fmi2SetContinuousStates(dlsym(lib, :fmi2SetContinuousStates), component,state_arr, n_states))
@test fmi2StatusOK == fmi2SetContinuousStates(dlsym(lib, :fmi2SetContinuousStates), component,state_arr, n_states)

state_arr = zeros(fmi2Real, 2)
test_status_ok(fmi2GetContinuousStates!(dlsym(lib, :fmi2GetContinuousStates), component,state_arr, n_states))
@test fmi2StatusOK == fmi2GetContinuousStates!(dlsym(lib, :fmi2GetContinuousStates), component,state_arr, n_states)
@test state_arr[2] == 2.0

n_indicators = Csize_t(2)
indicator_arr = zeros(fmi2Real, 2)
test_status_ok(fmi2GetEventIndicators!(dlsym(lib, :fmi2GetEventIndicators), component,indicator_arr, n_indicators))
@test fmi2StatusOK == fmi2GetEventIndicators!(dlsym(lib, :fmi2GetEventIndicators), component,indicator_arr, n_indicators)

nom_state_arr = zeros(fmi2Real, 2)
test_status_ok(fmi2GetNominalsOfContinuousStates!(dlsym(lib, :fmi2GetNominalsOfContinuousStates), component, nom_state_arr, n_states))
@test fmi2StatusOK == fmi2GetNominalsOfContinuousStates!(dlsym(lib, :fmi2GetNominalsOfContinuousStates), component, nom_state_arr, n_states)

der_arr = zeros(fmi2Real, 2)
test_status_ok(fmi2GetDerivatives!(dlsym(lib, :fmi2GetDerivatives), component,der_arr, n_states))
@test fmi2StatusOK == fmi2GetDerivatives!(dlsym(lib, :fmi2GetDerivatives), component,der_arr, n_states)
# Acceleration should be equal to Gravity in this FMU
@test der_arr[2] ≈ -9.81
if Sys.WORD_SIZE == 64
# on 32 Bit this returns 9.81 * 10^16 which is not equal to -9.81
@test der_arr[2] ≈ -9.81
end

test_status_ok(fmi2Terminate(dlsym(lib, :fmi2Terminate), component))
@test fmi2StatusOK == fmi2Terminate(dlsym(lib, :fmi2Terminate), component)
end
44 changes: 23 additions & 21 deletions test/FMI2/generic.jl
Original file line number Diff line number Diff line change
Expand Up @@ -20,78 +20,80 @@ function test_generic(lib, cblibpath, type::fmi2Type)
component = fmi2Instantiate(dlsym(lib, :fmi2Instantiate), pointer("test_generic"), type, pointer("{3c564ab6-a92a-48ca-ae7d-591f819b1d93}"), pointer("file:///"), Ptr{fmi2CallbackFunctions}(pointer_from_objref(get_callbacks(cblibpath))), fmi2Boolean(false), fmi2Boolean(false))
@test component != C_NULL

test_status_ok(fmi2SetDebugLogging(dlsym(lib, :fmi2SetDebugLogging), component, fmi2False, Unsigned(0), AbstractArray{fmi2String}([])))
test_status_ok(fmi2SetDebugLogging(dlsym(lib, :fmi2SetDebugLogging), component, fmi2True, Unsigned(0), AbstractArray{fmi2String}([])))
@test fmi2StatusOK == fmi2SetDebugLogging(dlsym(lib, :fmi2SetDebugLogging), component, fmi2False, Unsigned(0), AbstractArray{fmi2String}([]))
@test fmi2StatusOK == fmi2SetDebugLogging(dlsym(lib, :fmi2SetDebugLogging), component, fmi2True, Unsigned(0), AbstractArray{fmi2String}([]))

# fmi2SetupExperiment

test_status_ok(fmi2SetupExperiment(dlsym(lib, :fmi2SetupExperiment),component, fmi2Boolean(false), fmi2Real(0.0), fmi2Real(0.0), fmi2Boolean(false), fmi2Real(1.0)))
@test fmi2StatusOK == fmi2SetupExperiment(dlsym(lib, :fmi2SetupExperiment),component, fmi2Boolean(false), fmi2Real(0.0), fmi2Real(0.0), fmi2Boolean(false), fmi2Real(1.0))



# get, set and free State
state = fmi2FMUstate()
stateRef = Ref(state)

test_status_ok(fmi2GetFMUstate!(dlsym(lib, :fmi2GetFMUstate), component, stateRef))
@test fmi2StatusOK == fmi2GetFMUstate!(dlsym(lib, :fmi2GetFMUstate), component, stateRef)
state = stateRef[]

@test typeof(state) == fmi2FMUstate

test_status_ok(fmi2SetFMUstate(dlsym(lib, :fmi2SetFMUstate), component, state))
@test fmi2StatusOK == fmi2SetFMUstate(dlsym(lib, :fmi2SetFMUstate), component, state)
stateRef = Ref(state)

size_ptr = Ref{Csize_t}(0)
test_status_ok(fmi2SerializedFMUstateSize!(dlsym(lib, :fmi2SerializedFMUstateSize), component, state, size_ptr))
@test fmi2StatusOK == fmi2SerializedFMUstateSize!(dlsym(lib, :fmi2SerializedFMUstateSize), component, state, size_ptr)
size = size_ptr[]

serializedState = Array{fmi2Byte}(zeros(size))
test_status_ok(fmi2SerializeFMUstate!(dlsym(lib,:fmi2SerializeFMUstate), component, state, serializedState, size))
@test fmi2StatusOK == fmi2SerializeFMUstate!(dlsym(lib,:fmi2SerializeFMUstate), component, state, serializedState, size)

test_status_ok(fmi2DeSerializeFMUstate!(dlsym(lib, :fmi2DeSerializeFMUstate), component, serializedState, size, stateRef))
@test fmi2StatusOK == fmi2DeSerializeFMUstate!(dlsym(lib, :fmi2DeSerializeFMUstate), component, serializedState, size, stateRef)

@test stateRef[] != C_NULL
test_status_ok(fmi2FreeFMUstate(dlsym(lib,:fmi2FreeFMUstate), component, stateRef))
@test fmi2StatusOK == fmi2FreeFMUstate(dlsym(lib,:fmi2FreeFMUstate), component, stateRef)
@test stateRef[] == C_NULL



# # Initialization Mode

test_status_ok(fmi2EnterInitializationMode(dlsym(lib, :fmi2EnterInitializationMode), component))
@test fmi2StatusOK == fmi2EnterInitializationMode(dlsym(lib, :fmi2EnterInitializationMode), component)

fmireference = [fmi2ValueReference(16777220)]
test_status_ok(fmi2SetReal(dlsym(lib, :fmi2SetReal), component, fmireference, Csize_t(1), fmi2Real.([0.8])))
@test fmi2StatusOK == fmi2SetReal(dlsym(lib, :fmi2SetReal), component, fmireference, Csize_t(1), fmi2Real.([0.8]))

fmireference = [fmi2ValueReference(16777220)]
value = zeros(fmi2Real, 1)
test_status_ok(fmi2GetReal!(dlsym(lib, :fmi2GetReal), component, fmireference, Csize_t(1), value))
@test fmi2StatusOK == fmi2GetReal!(dlsym(lib, :fmi2GetReal), component, fmireference, Csize_t(1), value)
@test value == fmi2Real.([0.8])

fmireference = [fmi2ValueReference(637534208)]
value = zeros(fmi2Integer, 1)
test_status_ok(fmi2GetInteger!(dlsym(lib, :fmi2GetInteger), component, fmireference, Csize_t(1), value))
@test fmi2StatusOK == fmi2GetInteger!(dlsym(lib, :fmi2GetInteger), component, fmireference, Csize_t(1), value)

fmireference = [fmi2ValueReference(637534208)]
test_status_ok(fmi2SetInteger(dlsym(lib, :fmi2SetInteger), component, fmireference, Csize_t(1), fmi2Integer.([typemin(fmi2Integer)])))
@test fmi2StatusOK == fmi2SetInteger(dlsym(lib, :fmi2SetInteger), component, fmireference, Csize_t(1), fmi2Integer.([typemin(fmi2Integer)]))

fmireference = [fmi2ValueReference(637534208)]
value = zeros(fmi2Integer, 1)
test_status_ok(fmi2GetInteger!(dlsym(lib, :fmi2GetInteger), component, fmireference, Csize_t(1), value))
@test fmi2StatusOK == fmi2GetInteger!(dlsym(lib, :fmi2GetInteger), component, fmireference, Csize_t(1), value)
@test value == fmi2Integer.([typemin(fmi2Integer)])

# calculate ∂p/∂p (x)
posreference = [fmi2ValueReference(33554432)]
delta_x = fmi2Real.([randn()])
result = zeros(fmi2Real, 1)
test_status_ok(fmi2GetDirectionalDerivative!(dlsym(lib,:fmi2GetDirectionalDerivative), component, posreference, Csize_t(1), posreference, Csize_t(1), delta_x, result))

@test fmi2StatusOK == fmi2GetDirectionalDerivative!(dlsym(lib,:fmi2GetDirectionalDerivative), component, posreference, Csize_t(1), posreference, Csize_t(1), delta_x, result)
# ∂p/∂p(x) should be just x for any x
@test result ≈ delta_x

test_status_ok(fmi2ExitInitializationMode(dlsym(lib, :fmi2ExitInitializationMode), component))
if Sys.WORD_SIZE == 64
# GetDirectionalDerivative behaves weirdly on 32 Bit
@test result ≈ delta_x
end

@test fmi2StatusOK == fmi2ExitInitializationMode(dlsym(lib, :fmi2ExitInitializationMode), component)

test_status_ok(fmi2Reset(dlsym(lib, :fmi2Reset), component))
@test fmi2StatusOK == fmi2Reset(dlsym(lib, :fmi2Reset), component)

# # # fmi2FreeInstance
@test isnothing(fmi2FreeInstance(dlsym(lib, :fmi2FreeInstance), component))
Expand Down
11 changes: 2 additions & 9 deletions test/FMI2/utils.jl
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,6 @@
#
using ZipFile

function test_status_ok(status)
@test typeof(status) == fmi2Status
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

type checks are not necessary (redundant), because we will check for type stable functions in the next release

@test status == fmi2StatusOK
end

function test_status_discard(status)
@test typeof(status) == fmi2Status
@test status == fmi2StatusDiscard
end

function getFMU()
dlpath = Downloads.download("https://github.com/ThummeTo/FMIZoo.jl/raw/main/models/bin/Dymola/2023x/2.0/BouncingBallGravitySwitch1D.fmu")
Expand Down Expand Up @@ -87,6 +78,8 @@ function get_os_binaries()
end
elseif Sys.iswindows()
binarypath = joinpath(binarypath, "win32")
cblibpath = Downloads.download("https://github.com/halentin/FMIImport.jl/raw/main/src/FMI2/callbackFunctions/binaries/win32/callbackFunctions.dll")
cblibpath = cblibpath * "."
os_supported = true
else
os_supported = false
Expand Down