Bug 179990 - Provide a general support for parameterized type resolution bycustom OCL environments
Summary: Provide a general support for parameterized type resolution bycustom OCL envi...
Status: CLOSED FIXED
Alias: None
Product: OCL
Classification: Modeling
Component: Core (show other bugs)
Version: 1.1.0   Edit
Hardware: PC Windows XP
: P3 enhancement (vote)
Target Milestone: M4   Edit
Assignee: Christian Damus CLA
QA Contact:
URL:
Whiteboard: Extensibility
Keywords: api, contributed, noteworthy, plan
: 244144 (view as bug list)
Depends on:
Blocks:
 
Reported: 2007-03-29 09:56 EDT by Radomil Dvorak CLA
Modified: 2011-05-27 02:41 EDT (History)
4 users (show)

See Also:


Attachments
Resolving genericTypes.patch (9.28 KB, patch)
2007-03-29 10:02 EDT, Radomil Dvorak CLA
no flags Details | Diff
A proposed TypeChecker solution (11.17 KB, patch)
2008-11-05 17:30 EST, Christian Damus CLA
give.a.damus: review?
Details | Diff
ValidationVisitor patch (1.76 KB, patch)
2008-11-06 07:27 EST, Radomil Dvorak CLA
give.a.damus: iplog+
Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Radomil Dvorak CLA 2007-03-29 09:56:41 EDT
When trying to implement QVT Stdlib predefined types, I face a problem with
'List', 'Dictionary' types which extend OCL CollectionType.
 
As for conformance to CollectionType, it can be realized with the current implementation,
even though there is no clear contract for it. A subtype of the CollectionType
having its kind == collection is processed as a legal collection and
it simply seems working fine.
/* Of course, a clear contract for such extensions would be ideal  */
 
The only issue seems to be resolution of generic types on collections,
as the implementation resolves them in a kind of hardcoded way.
This is pretty OK for the OCL stdlib itself, but makes difficulties for QVT
StdLib::Dictionary type, which is also a parameterized type but coming with yet another
parameter 'keyT' (a HashMap like key type).
 
A general mechanism to resolve any generic types defined by a custom
environment would help here.
Comment 1 Radomil Dvorak CLA 2007-03-29 10:02:11 EDT
Created attachment 62385 [details]
Resolving genericTypes.patch
Comment 2 Christian Damus CLA 2008-08-14 09:26:04 EDT
*** Bug 244144 has been marked as a duplicate of this bug. ***
Comment 3 Adolfo Sanchez-Barbudo Herrera CLA 2008-08-14 09:54:35 EDT
Consider resolving

https://bugs.eclipse.org/bugs/show_bug.cgi?id=233673

to solve this one, specially, when a contribution has been provided ;)

The taken approach for the TypeUtil class, could be identically applied for the OCLStandardLibraryUtil class.

Cheers,
Adolfo.
Comment 4 Laurent Goubet CLA 2008-11-04 09:49:49 EST
Hi,

we've got a similar need for MTL. Now expecting the 1.3 release :).
Comment 5 Radomil Dvorak CLA 2008-11-05 15:28:23 EST
(In reply to comment #3)
It seems to be partly addressed by the concept introduced in https://bugs.eclipse.org/bugs/show_bug.cgi?id=233673.

However, I can still see couple of places in AbstractOCLAnalyzer, ValidationVisitor, which only call OCLStandardLibraryUtil.getResultTypeOf(...).
I would assume to delegate TypeChecker.getResultType(Object, C, O) for non-oclstdlib operations.

Another point is, why TypeChecker interface does not take into account operation arguments, when obtaining the operation result type. 
By extending that operation signature as written bellow, we could resolve generic parameters as well.
 
C getResultType(Object problemObject, C source, O oper, List<OCLExpression<C>> actualArgs)

If I have not missed anything ;), this way I should be able to support generic operations just by providing a custom TypeChecker implementation.
Comment 6 Christian Damus CLA 2008-11-05 16:17:00 EST
(In reply to comment #5)
> (In reply to comment #3)
> It seems to be partly addressed by the concept introduced in
> https://bugs.eclipse.org/bugs/show_bug.cgi?id=233673.
> 
> However, I can still see couple of places in AbstractOCLAnalyzer,
> ValidationVisitor, which only call OCLStandardLibraryUtil.getResultTypeOf(...).
> I would assume to delegate TypeChecker.getResultType(Object, C, O) for
> non-oclstdlib operations.

Right, I think we need to bring the OCLStandardLibraryUtil.getResultTypeOf(...) method into the TypeChecker API in the same way as the TypeUtil methods.  Then, these calls will be re-directed by the OCLStandardLibraryUtil to the TypeChecker.


> Another point is, why TypeChecker interface does not take into account operation
> arguments, when obtaining the operation result type.

Because it only implements the (old) TypeUtil::getResultType(...) API, which didn't account for arguments because it didn't need to consider parameter types that weren't covariant with the owner type.  However, that TypeUtil API wasn't used by the parser (probably because it didn't account for the actual arguments), so we should be able to get rid of it.


> By extending that operation signature as written bellow, we could resolve
> generic parameters as well.
> 
> C getResultType(Object problemObject, C source, O oper, List<OCLExpression<C>>
> actualArgs)

Yep.

> If I have not missed anything ;), this way I should be able to support generic
> operations just by providing a custom TypeChecker implementation.

Nope, you haven't missed anything.  :-)
Comment 7 Christian Damus CLA 2008-11-05 17:30:58 EST
Created attachment 117149 [details]
A proposed TypeChecker solution

Attached a patch that deprecates the existing TypeChecker::getResultType(...) operation in favour of a variant that accepts a list of the arguments of the operation call, for resolution of generic type variables in the parameter list.

I would rather delete the variant without the arguments than deprecate it, as it was new in this release.  How does everybody on the cc: list feel about that?

Radek and Alex, in particular, I would very much appreciate your review of this patch.
Comment 8 Radomil Dvorak CLA 2008-11-06 07:27:04 EST
Created attachment 117185 [details]
ValidationVisitor patch

I have found one place in ValidationVisitor.visitOperationCallExp(..), which should resolve possible generics too. Currently, the user operation is not given a chance to do so. See the attached patch.
If applied, my QVT scenarios work perfectly, Thanks!
Comment 9 Radomil Dvorak CLA 2008-11-06 07:52:59 EST
I have noticed one thing, which actually does not affect the functionality correctness but is rather a performance topic.
I can see a couple of redundant checks like bellow:
..
if ((sourceType instanceof PredefinedType)
	&& !env.getAdditionalOperations(sourceType).contains(oper)) {
..

It might look innocent for OCL ;), but in the QVT world it implies lookup through imported modules, thus imposing a certain penalty on all PredefinedType operations processing (especially if performed repeatedly).

1) done in AbstractOCLAnalyzer
2) done in ValidationVisitor
3) repeated in AbstractTypeChecker.getResultType(..)
   - though, here I can pretty simply figure out if it is a QVT defined operation and avoid delegation to the OCL default impl.

Could there be a faster, likely an OCL internal way of how to decide whether it is an additional operation?
Comment 10 Christian Damus CLA 2008-11-07 09:05:56 EST
(In reply to comment #8)
> Created an attachment (id=117185) [details]
> ValidationVisitor patch
> 
> I have found one place in ValidationVisitor.visitOperationCallExp(..), which
> should resolve possible generics too. Currently, the user operation is not
> given a chance to do so. See the attached patch.
> If applied, my QVT scenarios work perfectly, Thanks!

Thanks for the additional patch, and for testing this!

(In reply to comment #9)
> I have noticed one thing, which actually does not affect the functionality
> correctness but is rather a performance topic.
> I can see a couple of redundant checks like bellow:
> ..
> if ((sourceType instanceof PredefinedType)
>         && !env.getAdditionalOperations(sourceType).contains(oper)) {

Heh heh ... Yes, I noticed those, too, while I was working on this.

I was thinking of adding a method to the TypeChecker:

     isStandardLibraryFeature(C owner, Object feature)

to provide a single locus of implementation of this check.


> It might look innocent for OCL ;), but in the QVT world it implies lookup
> through imported modules, thus imposing a certain penalty on all PredefinedType
> operations processing (especially if performed repeatedly).
> 
> 1) done in AbstractOCLAnalyzer
> 2) done in ValidationVisitor
> 3) repeated in AbstractTypeChecker.getResultType(..)
>    - though, here I can pretty simply figure out if it is a QVT defined
> operation and avoid delegation to the OCL default impl.
> 
> Could there be a faster, likely an OCL internal way of how to decide whether it
> is an additional operation?

Well, as the type-checker is an object owned by the environment, it has an opportunity to cache results or be customized by the QVT environment with a suitably efficient algorithm.

Would this help?

Comment 11 Radomil Dvorak CLA 2008-11-10 07:30:38 EST
(In reply to comment #10)
The operation isStandardLibraryFeature(C owner, Object feature) would be useful.
Our check whether it's a QVT operation or not is not expensive and so we
can avoid eventual calls to the original implementation.
Comment 12 Christian Damus CLA 2008-11-12 10:45:24 EST
Applied my patch (attachment #117149 [details]).
Applied Radek's additional patch to ValidationVisitor(attachment #117185 [details]).
Added "List<? extends TypedElement<C>> args" parameter to TypeChecker::getResultType(...).
Added "boolean TypeChecker::isStandardLibraryFeature(C owner, Object feature)" operation along with corresponding TypeUtil static.

Comment 13 Christian Damus CLA 2008-11-23 17:50:41 EST
Fix available in HEAD: 1.3.0.I200811191813.
Comment 14 Ed Willink CLA 2011-05-27 02:40:07 EDT
Closing after over a year in verified state.
Comment 15 Ed Willink CLA 2011-05-27 02:41:45 EDT
Closing after over a year in verified state.