klayout icon indicating copy to clipboard operation
klayout copied to clipboard

pcell_declaration_helper's get_values() nullifies them?

Open kubaraczkowski opened this issue 4 years ago • 4 comments

Hi, Thanks for the great work!

I'm trying to use self.get_values() in produce_impl() of a python pcell.

However, it seems that after the first call the self._param_values is being set to None. What's the reason to do that? https://github.com/KLayout/klayout/blob/master/src/pymod/distutils_src/klayout/db/pcell_declaration_helper.py#L136

What this effectively does is that all parameters in the pcell are being set to None, which means a single call to get_values() 'destroys' the parameters.

kubaraczkowski avatar Mar 08 '21 08:03 kubaraczkowski

@kubaraczkowski

get_values is no function intended to be used by the implementor of the PCell. It's basically private, so ideally it should be called "_get_values" to reflect this fact.

The idea is the following: in order to simplify the implementation of a PCell, the PCellDeclarationHelper provides shortcuts for the parameter access. So if you declare a parameter "width", you will be able to read or write it's value through "self.width". This is kind of puzzling as the PCellParameterDeclaration is not representing a specific instance of a PCell, but it's rather descriptor object for the PCell and there is only one instance per PCell type. So how come it knows the parameter value of the instance considered?

Technically is feature is provided through the _PCellDeclarationHelperParameterDescriptor object and a temporary parameter hash. The _PCellDeclarationHelperParameterDescriptor acts as proxy to the actual value, so when you use "self.width", you actually access a _PCellDeclarationHelperParameterDescriptor which reads or writes the value in self._param_values. The latter is the temporary hash.

So whenever a the PCell code needs to provide some server, e.g. generating layout, KLayout will request this service through a low-level function called "produce" in this case. It will prepare self._param_values to contain the parameters for the PCell instance to be produced and call "produce_impl" which is the method you will provide when you use PCellDeclarationHelper. Because "self._param_values" is initialized with the instance parameter values, you can read the "width" value for example through "self.width".

Other functions like "parameters_from_shape" need to return parameters. They use the same mechanism, so when you reimplement "parameters_from_shape_impl" and use "sel.width = something", you will set the corresponding entry in "self._param_values". Finally, the implementation of "parameters_from_shape" will use "get_values" to read the values of "self._parame_values" and because that's the last thing this function does, it will tidy up after itself and nullify self._param_values.

TLDR: you don't need to use "get_values". Use "self.xyz" where "xyz" is the name of your parameter to read and write a value.

Matthias

klayoutmatthias avatar Mar 22 '21 13:03 klayoutmatthias

Was the reply helpful? I want to close this issue as that isn't a real bug.

klayoutmatthias avatar Apr 14 '21 21:04 klayoutmatthias

Hi Matthias, Sorry for the late reply! Yes, the reply is very useful indeed. I do understand the get_values() would be better called __get_values().

Maybe the issue should become a feature request then, on how to programmatically get the list of pcell parameters with their current values.Perhaps my implementation is a special case, but what I made is a layered structure where the higher layers of pcells "inherit" parameters from lower level cells.I implemented it by having a list of parameters 'outside' of both which then is added (and passed) through the layered system. Trouble is - by doing so the higher-level cells don't actually know the parameters to be called by e.g self.width. What I do to collect them and pass deeper is:

settings = {x.name:y for x,y in zip(self.get_parameters(), self._param_values)}

Otherwise - fine to close the issue! And thanks for the fantastic work

kubaraczkowski avatar Apr 19 '21 08:04 kubaraczkowski

@kubaraczkowski I'm sorry, I just came across this old issue and found I did not respond.

I'll schedule a change such that "get_values" returns the values without nullifying them and update the documentation.

Matthias

klayoutmatthias avatar Feb 16 '22 21:02 klayoutmatthias