Block not being executed in time.

Send to friendSend to friend

Hello.

I am developing a DLL plug-in for IAPWS-95 steam properties.

Background:

Before I get to my specific problem I will explain in some detail the implementation of my plug-in and it's use. I am playing some games with the Vissim matrix parameter type that needs a bit of explaining. I am doing this mainly for calculating speed. Normally the IAPWS-95 is slow and most use the IFC-97 formulations. But the IAPWS-95 I think is the better choice for simulation. They do not divide the calculations into regions that cause problems crossing region boundaries. It also has additional properties that allow for a very fast isentropic change simulation. The way I am implementing this is to increase it's speed by avoiding recalculations. Many properties share subsets of calculations that needn't be calculated over and over. In my implementation I cash these values and do not recalculate them until an input change requires their recalculation. If for example you look at the formula for pressure, internal energy, entropy, and enthalpy you see that they all have common sub function of the Helmholtz equations. And the Helmholtz equation have common parts as well. They are first and second order derivatives of the main Helmholtz function so that is expected. For example they use T (temperature reduced unitless) to various powers. These are precalculated when temperature is set. Only the properties that are required are calculated. It would be nice if Vissim had a structure type argument to blocks. Or explained what and how this typedef is used.

typedef enum { S_NULL, S_SCALAR, S_VECTOR, S_MATRIX, S_STRUCT, S_LAST } SHAPE;

The IAPWS-95 steam properties are calculated from temperature and density with a single set of formula that cover the entire range except for the saturated mixture region where they are calculated as a mixture of the vapor and liquid states. The plug-in implements the calculations as a set of blocks. There are three types of blocks: StatePoint, input conversion, and output retrieval conversion. StatePoint blocks take input property sets: (temperature, density), (pressure, temperature), (temperature) and (pressure)... The (pressure) and (temperature) blocks can have an added input for quality and become (pressure, quality) and (temperature, quality). The input to StatePoint blocks are unit-less internal scalars. I have other StatePoint blocks to be implement that would add inputs for entropy, enthalpy, internal energy, etc. The scalar to scalar "input conversion blocks" convert properties to the unit-less scalar inputs of the StatePoint blocks. There are input conversion blocks for pressure, temperature, specific volume, internal energy, enthalpy and entropy. The output of the StatePoint blocks are a c++ class structure. This class structure is disguised as a Vissim matrix:

typedef struct IAPWSMATRIX { char isTemp; unsigned dim1; unsigned dim2; unsigned dim3; IAPWSMATRIX *next; IAPWS_StatePoint sp; } IAPWSMATRIX;

The StatePoint blocks "param"s is:

typedef struct { unsigned char iports; IAPWSMATRIX VsMat; } IAPWS_Pt;

and it's output is the VsMat.

My third type of block "output retrieval conversion" take the IAPWSMATRIX output by the StatePoint block as input. Properties are not calculated by the StatePoint block but by the "output retrieval conversion" blocks. The IAPWS_StatePoint class contains all the property calculation methods and the retrieval conversion blocks call the StatePoint class to get properties. For example the entropy block implementation is:

EXPORT32 void PASCAL i_s(IAPWS_CV* U, IAPWSMATRIX* inSig[], double outSig[]){ // specific entropy if ((inSig[0]->sp.flags & ttf) && (inSig[0]->sp.flags & tdf)) // are temperature and density set outSig[0] = Entropy_factor[U->units] * inSig[0]->sp.os();} // Calculate entropy and convert to units.

NOTE. The unitless value may be retrived by the above. unitless is a conversion option.

I have created a property that gives dT/dd|s. Rate of change of temperature with respect to density along a line of constant entropy. So with the rate of change of density with respect to time, dd/dt I can get dT/dt = dT/dd * dd/dt. And with dd/dt and dT/dt and can do isentropic density changes with integrators to get temperature and density. With a straight forward test using a constant dd/dt and a multiply block taking dd/dt and dT/dd going to a (temperature, density) StatePoint block by way of integrator blocks with appropriate initial values and dT/dd coming from that state point block it works fine. I have a test doing an isentropic expansion from 1500 PISA to 275 PSIA with entropy constant to 12 places. But I haven't got dT/dd working in the saturated mixture region. So I have it stopping at the saturation line. It is doing around 150,000 steps in an actual time of 3.4 seconds running on an AMD 2.7 gig processor.

The test case I am having a problem with is simulating an isentropic flow through a tube section.

I am trying to simulate by-directional dynamic flow through passage ways. I.E. A piston steam engine with valves opening and closing creating harmonic pressure waves. All right I'm a steam nut. I am doing this package for my own use in developing a reciprocating steam engine.

A section is using the (temperature, density) StatePoint block in much the same fashion as described above in the constant dd/dt test case. But for the by simulate by-directional case the steam is accelerating.

To calculate the acceleration and speed of the flow and ultimately the density change with respect to time for this section I need the next and previous sections pressure.

The problem I am having is getting every thing initialized. I have a test case of 5 sections. I am getting no complaint of an algebraic loop. I am taking the difference if the previous and currant sections pressure and the difference of the next and current sections pressure in calculating the acceleration. After first loading the test case I get errors on my "output retrieval conversion" blocks because of invalid inputs. The StatePoint blocks are not getting calculated using the initial values in the integrator blocks. Doing a single step and reset Sim a few times gets all going an then it works. Why are my "output retrieval conversion" blocks being called when their StatePoint block hasn't. The integrator blocks are getting their initial values from variables that are set from the previous sections temperature and density.

I am doing this for my own use. I am a retired software engineer. I have Vissim 4.5B I got with MathCad 2001 while a taking an engineering course. I can not afford to upgrade. I have tried several things to get these initilized. Tried using VR_EXECUTE at sim start. But caused an error. My "output retrieval conversion" blocks are being called with invalid memory addresses causing invalid memory referances. This seams to be a problem with the intergrator blocks not being called. But when I put display blocks tham the show valid values, yet the state point block is not being called with them.

Andy

Wow, you've done some impressive work!

Hi Andy, You have done a lot of work on this. Unfortunately, the version you are using, 4.5, is around 10 years old and no longer supported. Can you download a trial of version 8 and see how it works for you? It will run for 2 months. You say you can't afford to upgrade, but since you are "retired" and doing add-on development you can ask sales for special consideration on a developers upgrade license. Maybe you can swap your steam properties plugin for a full up v8 license.

Thanks for the reply. I will

Thanks for the reply.

I will try an get in contact with sails. Right now I am fighting another problem that is causing me a bit of a problem. After makeing a change to my plugin vissim is craching somewere in vissim.lib when I try to load a test file. I have looked at the .vsm file and one I created and save after the change and don't see any real differances.

I think my origional problem was that the intergrator blocks were not being called initially to output their initial conditions. Is that some thing that has been a problem. Shouldn't they be "VBF_HAS_STATE" blocks to output their initial condition? I don't think that is happing for when my block, to get statepoint properties, is called the statepoint block has not been called. All my blocks return zero 0 on creation so none should be set to have initial values.

I didn't get an email of your response. I think my acount is set to send me an email on a response. I checked here several times and the response didn't show until I loged in. "Notify me when new comments are posted" and "Replies to my comment" are checked. Does "All comments" need to be checked.

I will see what I can work out with your sails department.

Andy