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

Changed the comparators for Resource, Capability, and Requirement #5807

Conversation

pkriens
Copy link
Member

@pkriens pkriens commented Oct 12, 2023


Signed-off-by: Peter Kriens Peter.Kriens@aQute.biz

---
 Signed-off-by: Peter Kriens <Peter.Kriens@aQute.biz>

Signed-off-by: Peter Kriens <Peter.Kriens@aQute.biz>
@pkriens
Copy link
Member Author

pkriens commented Oct 12, 2023

Fixes #5793

@pkriens
Copy link
Member Author

pkriens commented Oct 12, 2023

@mnlipp could you take a look at these changes?

@pkriens pkriens requested a review from amitjoy October 12, 2023 07:22
---
 Signed-off-by: Peter Kriens <Peter.Kriens@aQute.biz>

Signed-off-by: Peter Kriens <Peter.Kriens@aQute.biz>
---
 Signed-off-by: Peter Kriens <Peter.Kriens@aQute.biz>

Signed-off-by: Peter Kriens <Peter.Kriens@aQute.biz>
@mnlipp
Copy link
Contributor

mnlipp commented Oct 12, 2023

@mnlipp could you take a look at these changes?

I will. Just have to solve some other problem first in order to test it in my environment.

@kriegfrj kriegfrj changed the title Changed the comparators for Resource, Capabiity, and Requirement Changed the comparators for Resource, Capability, and Requirement Oct 13, 2023
@kriegfrj
Copy link
Contributor

Fixes #5807

Haven't had a detailed look at the fix, but the "Fixes #5807" text should go in one or more of the commits too, no?

@pkriens
Copy link
Member Author

pkriens commented Oct 13, 2023

@kriegfrj I guess :-) When I get this one merged, I'll close #5807

Thanks for engaging.

@mnlipp
Copy link
Contributor

mnlipp commented Oct 13, 2023

In order to test your version, I've upgraded everything in my environment to 7.0.0. Nice effect: resolution works again without problems (for whatever reason; I assume that there is no difference between the 6.4.x comparator and the 7.0.0 comparator).

Then I've build the p2 repository from your PR and installed it into eclipse. Now the resolution fails (doesn't terminate). I've appended the last entries from the log. I won't claim that I understand this. Failure is somehow always related to the felix webconsole, no matter how long I wait. I've tried putting some things on the blacklist that are not part of my previous (7.0.0) successful solution (e.g. org.apache.tomcat-servlet-api -- I don't need that, so I assumed that it "prunes" some possibilities) but this didn't help. (Interestingly, org.apache.tomcat-servlet-api [org.apache.tomcat-servlet-api still appears in the log even when it is on the blacklist, no idea if this is okay or another problem.)

...
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6] because it is exposed to package 'javax.servlet.http' from resources org.apache.tomcat-servlet-api [org.apache.tomcat-servlet-api version=9.0.80] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] via two dependency chains.

Chain 1:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.0.0)(!(version>=5.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http
  org.apache.tomcat-servlet-api [org.apache.tomcat-servlet-api version=9.0.80]

Chain 2:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    require: (&(osgi.implementation=osgi.http)(version>=1.1.0)(!(version>=2.0.0)))
     |
    provide: osgi.implementation;uses:='javax.servlet,javax.servlet.http,org.osgi.service.http.context,org.osgi.service.http.whiteboard';osgi.implementation='osgi.http';version:Version='1.1.0'
  org.apache.felix.http.bridge [org.apache.felix.http.bridge version=4.1.2]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0])
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6] because it is exposed to package 'javax.servlet.http' from resources org.apache.tomcat-servlet-api [org.apache.tomcat-servlet-api version=9.0.80] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] via two dependency chains.

Chain 1:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.0.0)(!(version>=5.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http
  org.apache.tomcat-servlet-api [org.apache.tomcat-servlet-api version=9.0.80]

Chain 2:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    require: (&(osgi.implementation=osgi.http)(version>=1.1.0)(!(version>=2.0.0)))
     |
    provide: osgi.implementation;uses:='javax.servlet,javax.servlet.http,org.osgi.service.http.context,org.osgi.service.http.whiteboard';osgi.implementation='osgi.http';version:Version='1.1.0'
  org.apache.felix.http.bridge [org.apache.felix.http.bridge version=4.1.2]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0])
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.http.jetty [org.apache.felix.http.jetty version=4.2.18] because it is exposed to package 'javax.servlet' from resources org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=1.2.0] via two dependency chains.

Chain 1:
  org.apache.felix.http.jetty [org.apache.felix.http.jetty version=4.2.18]
    import: (&(osgi.wiring.package=javax.servlet)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0]

Chain 2:
  org.apache.felix.http.jetty [org.apache.felix.http.jetty version=4.2.18]
    require: (&(osgi.contract=JavaServlet)(version=3.1))
     |
    provide: osgi.contract: JavaServlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=1.2.0])
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6] because it is exposed to package 'javax.servlet' from resources org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.1.0] via two dependency chains.

Chain 1:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    import: (&(osgi.wiring.package=javax.servlet)(version>=3.0.0)(!(version>=5.0.0)))
     |
    export: osgi.wiring.package: javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0]

Chain 2:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    require: (&(osgi.implementation=osgi.http)(version>=1.1.0)(!(version>=2.0.0)))
     |
    provide: osgi.implementation;uses:='javax.servlet,javax.servlet.http,org.osgi.service.http.context,org.osgi.service.http.whiteboard';osgi.implementation='osgi.http';version:Version='1.1.0'
  org.apache.felix.http.bridge [org.apache.felix.http.bridge version=4.1.2]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http; uses:=javax.servlet
    export: osgi.wiring.package=javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.1.0])
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6] because it is exposed to package 'javax.servlet' from resources org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.1.0] via two dependency chains.

Chain 1:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    import: (&(osgi.wiring.package=javax.servlet)(version>=3.0.0)(!(version>=5.0.0)))
     |
    export: osgi.wiring.package: javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0]

Chain 2:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    require: (&(osgi.implementation=osgi.http)(version>=1.1.0)(!(version>=2.0.0)))
     |
    provide: osgi.implementation;uses:='javax.servlet,javax.servlet.http,org.osgi.service.http.context,org.osgi.service.http.whiteboard';osgi.implementation='osgi.http';version:Version='1.1.0'
  org.apache.felix.http.bridge [org.apache.felix.http.bridge version=4.1.2]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http; uses:=javax.servlet
    export: osgi.wiring.package=javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.1.0])
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.http.jetty [org.apache.felix.http.jetty version=4.2.18] because it is exposed to package 'javax.servlet' from resources org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=1.2.0] via two dependency chains.

Chain 1:
  org.apache.felix.http.jetty [org.apache.felix.http.jetty version=4.2.18]
    import: (&(osgi.wiring.package=javax.servlet)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0]

Chain 2:
  org.apache.felix.http.jetty [org.apache.felix.http.jetty version=4.2.18]
    require: (&(osgi.contract=JavaServlet)(version=3.1))
     |
    provide: osgi.contract: JavaServlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=1.2.0])
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6] because it is exposed to package 'javax.servlet' from resources org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.0.0] via two dependency chains.

Chain 1:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    import: (&(osgi.wiring.package=javax.servlet)(version>=3.0.0)(!(version>=5.0.0)))
     |
    export: osgi.wiring.package: javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0]

Chain 2:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    require: (&(osgi.implementation=osgi.http)(version>=1.1.0)(!(version>=2.0.0)))
     |
    provide: osgi.implementation;uses:='javax.servlet,javax.servlet.http,org.osgi.service.http.context,org.osgi.service.http.whiteboard';osgi.implementation='osgi.http';version:Version='1.1.0'
  org.apache.felix.http.bridge [org.apache.felix.http.bridge version=4.1.2]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http; uses:=javax.servlet
    export: osgi.wiring.package=javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.0.0])
DEBUG: Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6] because it is exposed to package 'javax.servlet' from resources org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0] and org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.0.0] via two dependency chains.

Chain 1:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    import: (&(osgi.wiring.package=javax.servlet)(version>=3.0.0)(!(version>=5.0.0)))
     |
    export: osgi.wiring.package: javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=3.0.0]

Chain 2:
  org.apache.felix.webconsole [org.apache.felix.webconsole version=4.9.6]
    require: (&(osgi.implementation=osgi.http)(version>=1.1.0)(!(version>=2.0.0)))
     |
    provide: osgi.implementation;uses:='javax.servlet,javax.servlet.http,org.osgi.service.http.context,org.osgi.service.http.whiteboard';osgi.implementation='osgi.http';version:Version='1.1.0'
  org.apache.felix.http.bridge [org.apache.felix.http.bridge version=4.1.2]
    import: (&(osgi.wiring.package=javax.servlet.http)(version>=3.1.0)(!(version>=4.0.0)))
     |
    export: osgi.wiring.package: javax.servlet.http; uses:=javax.servlet
    export: osgi.wiring.package=javax.servlet
  org.apache.felix.http.servlet-api [org.apache.felix.http.servlet-api version=2.0.0])

@chrisrueger
Copy link
Contributor

@mnlipp
Copy link
Contributor

mnlipp commented Oct 13, 2023

Sorry, I cannot be more helpful here.

Thanks. Eventually, I'll have to blacklist until things work, done that before. In this special context, however, the question is whether this PR "breaks" something. I would have expected that modifying the comparator has effects on the time required to find the solution. I wouldn't have been surprised if the solution found was slightly different But I find it surprising that the "known solution" isn't found any more.

@pkriens
Copy link
Member Author

pkriens commented Oct 16, 2023

@tjwatson could you take a quick look at the diagnosis and see if you recognize the problem?

@mnlipp can you share the the whole debug log?

@mnlipp
Copy link
Contributor

mnlipp commented Oct 16, 2023

Log file attached. (Project is https://github.com/mnlipp/jgrapes-osgi/commits/master (968cf2d6640e7b923fc139258c91a61582cdda1f), resolving org.jgrapes.osgi.demo.console/democonsole.bndrun.)

tmp13821316911941492298.log.gz

@pkriens
Copy link
Member Author

pkriens commented Oct 16, 2023

Hmm. These are you providers for the javax.servlet.http package:

image

Http servlet might not be the absolute worst API in Java, from an OSGi point of view developers have tried since the heydays of EE server to give OSGi a really hard time making every bad semantic versioning and API decision that mankind could possibly come up with.

You're torturing the resolver beyond my imagination :-)

  • Two versions of Tomcat Servlet API,
  • Ten versions of the Felix http API?
  • Three times httplite?
  • And last and least, 3x javax servlet API. And I am ignoring the Jakarta jars.

Eighteen choices! And then I am not counting that all those JARs lie through their teeth that they support multiple versions for these packages since semantic versioning was not on the radar in the EE world. So the resolver probably sees 40 or 50 candidates. That is really not what it was designed for.

I am really happy that you made me cleanup the comparators, they were really awfully bad. However, one of the wisest lessons of Elon Musk is not to optimize a solution, but try to get rid of the problem altogether. It has been my motto all my life, a better design is when it has fewer potential error cases.

I think we need to figure out why the solution does not resolve on Apache/Eclipse and I've asked Eclipse's @tjwatson to look over our shoulders.

From a bndtools point of view I think the solution for you is trivial, you have to clean up your repositories. The problem you run into is closely associated with #4172, you're having WAY too many options for the resolver. Also in bndtools, the resolution took > 20 seconds on an M2 chip. I haven't got a single bndrun file that takes more than 3 secs to resolve.

By having this many options for the servlet (and associated) packages you are begging on your knees for resolver issues.

I really appreciate helping to make the resolver better and the work you did. Very welcome. But I suggest we move the log and a commit record of your project and attach it to #4172 because I am pretty sure you've run into this bug.

On your site, get rid of all but one servlet API JAR and your resolve will be sub second and more reliable ... Imho, keeping the repository's small saves a tremendous amount of issues, a lot of complicated things tend too get trivial.

What do you think?

@tjwatson
Copy link
Contributor

Can you describe what you are fixing here. It says fixing #5807, but that is this PR.

There were previous issues in BND where the comparator for BND resources was clearly wrong and that caused issues with BND and the resolver. But I find it hard to tell (only looking for a little bit) what this PR is fixing or the behavior it changed.

@pkriens
Copy link
Member Author

pkriens commented Oct 16, 2023

@tjwatson sorry. the bug is #5793 but I don't think you're that concerned about it. I've changed the comparators in bnd since they were terrible and did not give consistent ordering. However, @mnlipp, who reported a sorting error due to the instability of the ordering, now has a resolution that succeeds on bndtools but fails on Eclipse.

I was just asking if you could take a look at the log output in this bug and see if you maybe recognize the issue, the resolver loops forever. In the mean time I found out the project had 18 (!) jars with the servlet packages in myriad versions. It looks to me like the Apache Felix #4172 (comment) problem?

@mnlipp
Copy link
Contributor

mnlipp commented Oct 16, 2023

What do you think?

Two things:

(1) As I don't have a release manager for my OSS projects, I rely on the conventional strategy of trying to use the latest version of each bundle. (These may introduce new bugs but they should fix known security issues.) In order to automate this, my repository plugin scans the maven repositories starting with some explicitly given groups and lower bounds for artifacts and generates an index of these and all their dependencies (yes, the resulting index/repository is too big). All providers for the javax.servlet.http package that are in the "IndexedMaven" repository are actually dependencies of some other bundles, none was included explicitly.

From time to time, I raise the lower bounds for the artifacts to reduce the number of bundles in the (generated) repository, but specific selections for my application (when required) are mostly managed by blacklisting bundles. This might push the resolver to its limits, but I've always thought that this is what it was made for. Yes, it takes some time, but I know that the underlying problem is difficult and, hey, how often do you have the opportunity to really see your hardware investment paying off.

Unless this PR introduces some "fatal" issue, I will eventually get the resolution working again by adjusting my repository. And I understand that I should try to do this (and will within the next days) in order to provide additional input for evaluating this PR.

(2) I still consider it strange that this PR breaks the resolution. I only had a superficial look at the code, and from this it looks like a rewrite. So, complicated as my resolution scenario may be, I wonder if it happens to be the missing (unit)test that reveals a regression bug introduced by this PR. And if this is the case, the PR might eventually not only break my resolving but also other's. If I was responsible for QA, I'd at least insist on some more non-trivial scenarios to be tested with this PR in place and check if they still resolve.

@tjwatson
Copy link
Contributor

I think we need to figure out why the solution does not resolve on Apache/Eclipse and I've asked Eclipse's @tjwatson to look over our shoulders.

I think I misunderstood the ask of me. So this is an issue trying to install the latest local build of the development branch+PR changes into an Eclipse installation and the resolution error is coming from that? Or is this error happening from some resolution driving from BND which is not using this PR?

@pkriens
Copy link
Member Author

pkriens commented Oct 17, 2023

@tjwatson sorry for not being more clear, my brain turning mush :-(

  • A bndrun file is resolved
  • Turned into p2 repo
  • Installed in Eclipse
  • Resolve never ends ...

@mnlipp This is the story, isn't it?

The thing is, I've changed the comparators of Resource, Capability, and Requirement so it is kind of a conincedence that it now fails. However, there are 18 Jars with the servlet packages which each have numerous versions so it looks like a prime candidate for the resolver bug. I just wanted you to take a quick look if the log looked familiar with the resolver bug where a resolution never ends.

@pkriens
Copy link
Member Author

pkriens commented Oct 17, 2023

@mnlipp I just believe in a very clean work floor to keep productivity up. That said, in maven they at least pick the first encountered version of an artifact. You seem to include multiple versions of the same artifact. This would already solve this problem I think.

I still consider it strange that this PR breaks the resolution.

I do not think this PR breaks the resolution in any way. Let's assume the bundles we give Eclipse are not a valid solution. The resolver in Eclipse should then tell is why it is bad. There is just no input we could possible give to Eclipse that would warrant not resolving. I.e this by definition is a bug in Eclipse/Apache resolver setup. No input should be able to create this behavior.

I always hate these kind of 'coincidences' since they are extremely rare in our world. When two things happen at the same time they are almost always related. However, in this case Eclipse/Apache is by definition wrong by not resolving or claiming there is no resolution. Those are the only two valid outcomes of the API. Without this resolve bug out of the way, there is nothing we can do. I am also pretty confident that if bndtools found a solution, there is is a solution. I've not printed out the wiring yet to inspect it by hand. Kept back by my PTSD of servlets, it feels like having to dive in a cave filled with snakes :-(

@pkriens
Copy link
Member Author

pkriens commented Oct 18, 2023

So @mnlipp, what do we do? I am inclined to submit this PR and see what happens?

@bndtools/maintainers any feedback to not merge this?

@mnlipp
Copy link
Contributor

mnlipp commented Oct 18, 2023

I am, just now, trying to get the resolution working again (sorry, didn't have time to do it earlier). I've reduced the number of servlet apis. Now (2 minutes ago) I get

Resolution failed. Capabilities satisfying the following requirements could not be found:
    [<<INITIAL>>]
      ⇒ osgi.identity: (osgi.identity=de.mnl.osgi.log4j2osgi)
          ⇒ [de.mnl.osgi.log4j2osgi version=1.2.0.ga]
              ⇒ osgi.wiring.package: (&(osgi.wiring.package=org.apache.logging.log4j)(version>=2.16.0)(!(version>=3.0.0)))
                  ⇒ [org.apache.logging.log4j.api version=2.21.0]
                      ⇒ bnd.multirelease: (&(bnd.multirelease=org.apache.logging.log4j.api)(&(version>=2.21.0)(version<=2.21.0)))

I've never seen this before and I'm currently trying to understand it (log4j-api with version 2.21.0 is in my repository). I don't know yet whether this is related to this PR and wasn't "visible" before because of the never ending resolution or whether this is a completely independent issue. It's up to you to wait some more hours and see if something else shows up in my "special environment" or submit the PR now...

@mnlipp
Copy link
Contributor

mnlipp commented Oct 18, 2023

New start. Went back to bnd-7.0.0. Excluded some of the javax.servlet bundles. Speeds up resolving tremendously (without changing the result).

Installed this PR version. Resolving works. Regrettably, it takes more time, but I won't complain about that, I know that I'm "torturing the resolver".

There is one difference in the result. This (PR) version adds org.osgi.service.http.whiteboard to the runbundles (has never been added when using bnd-7.0.0 or previous versions). The reasoning seems plausible, though:

image

(Looks like not adding it was a bug in the solution found by bnd-7.0.0, though the lack of this bundle has never caused any problems.)

To summarize: time required to resolve has changed, result has slightly changed. This is what I'd expect from such a modification.

@pkriens
Copy link
Member Author

pkriens commented Oct 18, 2023

so to make you co-responsible when it fails :-), shall we merge? I think this code is a lot better than the previous, it had a lot of known errors. I've been extremely careful to check for potential NPE's.

@mnlipp
Copy link
Contributor

mnlipp commented Oct 18, 2023

so to make you co-responsible when it fails :-), shall we merge?

Well, go ahead.

@tjwatson
Copy link
Contributor

tjwatson commented Oct 18, 2023

The thing is, I've changed the comparators of Resource, Capability, and Requirement so it is kind of a conincedence that it now fails. However, there are 18 Jars with the servlet packages which each have numerous versions so it looks like a prime candidate for the resolver bug. I just wanted you to take a quick look if the log looked familiar with the resolver bug where a resolution never ends.

I haven't had time to dig into this in details. But it does sound like the resolver is simply overwhelmed trying to solve the NP-hard problem with the number of possible choices. There are two things that usually help when installing such atrocities.

  1. Start eclipse with -clean so that it re-installs all the bundles and resolves from scratch. This makes it possible to make more optimized decisions early such that it can find a solution faster.
  2. Add the property equinox.resolver.revision.batch.size=1 to the config.ini file of your eclipse installation. This forces the framework to resolve bundles one at a time so that each resolver call has a drastically reduced set of decisions to make allowing for a much easier problem to solve.

@kriegfrj
Copy link
Contributor

To summarize: time required to resolve has changed, result has slightly changed. This is what I'd expect from such a modification.

It would be interesting to see if the increased time to resolve is because of the different path that the resolver took to find a solution (ie, more iterations) or if because the comparator itself was slower (similar number of iterations but slower). The fact that it added an extra bundle suggests the former, but perhaps this is something we should try and keep an eye on during testing.

@pkriens
Copy link
Member Author

pkriens commented Oct 25, 2023

This is mostly in the resolve context where we use it to order. It would not surprise me if we sort more often than necessary. Looking at what I know about the resolve process, would surprise me if the comparator would make a visible difference.

@mnlipp
Copy link
Contributor

mnlipp commented Oct 25, 2023

Please note that I didn't systematically measure the time! My remark was based on an observation made when switching from one version to the other, which implied a restart of Eclipse. Although I am quite sure that I also had (re-)started Eclipse before the switch to verify the "old" resolution, all kinds of causes may have had an effect on that single observation.

Especially that fact that the result of the old (re-tested) resolve process was what was already given while this PR version found a slightly different result may have had a significant effect. Better measurements would be required before pondering too much about this.

@kriegfrj
Copy link
Contributor

I agree... I don't think it's worth the effort to benchmark formally/accurately. But I do think that it is worth us as alpha testers keeping an eye on it in case any significant performance changes are noted by any of us - that might warrant closer investigation.

@pkriens pkriens merged commit d93f555 into bndtools:master Oct 25, 2023
9 checks passed
@tjwatson
Copy link
Contributor

I agree... I don't think it's worth the effort to benchmark formally/accurately. But I do think that it is worth us as alpha testers keeping an eye on it in case any significant performance changes are noted by any of us - that might warrant closer investigation.

Perhaps, but this is largely a concern of the Felix resolver implementation and its use in Equinox vs. anything BND tools can do.

@chrisrueger
Copy link
Contributor

I may have something related to this issue here. I don't know if it is problematic or not. I just noticed a difference between 7.0.0 and 7.1 in the resolver result:

Requirement was: com.jcraft.jsch [0.1.0,1.0.0)

7.0.0 picked
image

osgi.wiring.bundle;
	bundle-version = 0.1.55.v20190404-1902;
	osgi.wiring.bundle = com.jcraft.jsch

osgi.wiring.package;
	bundle-symbolic-name = com.jcraft.jsch;
	bundle-version = 0.1.55.v20190404-1902;
	osgi.wiring.package = com.jcraft.jsch;
	version = 0.1.55;
	bnd.hashes = [2000715872, -703989888, -1632970141, 1682692232, -1891363613, 361435263, -1298758276, 1941575700, 2024042338, -83369850, 1666531826, -478401337, 166809651, -2137403731, 2090270475, 1526275082, -2037877338, -1534621073, 1454689250, 1941975954, 71757581, 1317690060, 62647477, 2018562603, 1645930499, -1195114170, 264950860, 2180, -1947191567, -1947190515, -1947188782, 65012844, 2097230, 65014182, 65014838, -173161891, 2122146, 488601800, 478131912, 2210062, -1531639945, 1757419041, 2342, -71117602, 43163514, -1034806157, 515215048, 2287470, 1949294047, 310477953, -475355116, -1899599486, 2018645, -44281222, 849069497, 1567046969, -1600931301, 2000632667, -1536903235, 2000646121, -1590535212, 1567060423, -681174902, -1468810648, -523935405, -2013470288, 76079, -1204752338, -947445728, 75922139, -1911998296, 841424347, 77388366, 1527579606, -565019437, -565019436, -1854418717, 2014597491, 2030550014, -1477449824, 2116703416, -1477049570, 1456148737, -2103044617, -1652268352, -911026225, 2030566313, 903012212, -1693962467, 1265182974, -645326218, 823454131, -1933087520, 174416446, 789791136, -1217415016, -1306826246, -1729119588, -1306812792, 215032311, 415746375, -202390477, -1873834213, 971478344, 828478987, -806223890, -1143057341, -202159303, 2647074]

osgi.wiring.package;
	bundle-symbolic-name = com.jcraft.jsch;
	bundle-version = 0.1.55.v20190404-1902;
	osgi.wiring.package = com.jcraft.jsch.jce;
	version = 0.1.55;
	bnd.hashes = [573506460, 573507033, 579792361, 579792934, 604846592, 604847165, -30172584, -1223236385, -1223235333, -759752102, 2180, -1203608207, -1203607155, -1203605422, 65786604, 2221031, 1742301239, -685752940, -1823053428, 392314281, 392315118, 392317873, 2000632667, -1536903235, 2000646121, 76158, 75922139, -1854418717, 2543909, -1850268089, -1850267037, -1850265334, -1306826246, 1636151863, 1636152915, 1636154648, -2063099598, -1306812792, 235061392, 235061965];
	uses := com.jcraft.jsch

osgi.wiring.package;
	bundle-symbolic-name = com.jcraft.jsch;
	bundle-version = 0.1.55.v20190404-1902;
	osgi.wiring.package = com.jcraft.jsch.jcraft;
	version = 0.1.55;
	bnd.hashes = [-1195114170, 2221031, 1742301239, -685752940, -1823053428, 392314281];
	uses := com.jcraft.jsch

osgi.wiring.package;
	bundle-symbolic-name = com.jcraft.jsch;
	bundle-version = 0.1.55.v20190404-1902;
	osgi.wiring.package = com.jcraft.jsch.jgss;
	version = 0.1.55;
	bnd.hashes = [-723852638];
	uses := com.jcraft.jsch

7.1. (master) picked:

image
osgi.wiring.bundle;
	bundle-version = 0.1.55.1;
	osgi.wiring.bundle = org.apache.servicemix.bundles.jsch

osgi.wiring.package;
	bundle-symbolic-name = org.apache.servicemix.bundles.jsch;
	bundle-version = 0.1.55.1;
	osgi.wiring.package = com.jcraft.jsch;
	version = 0.1.55;
	bnd.hashes = [2000715872, -703989888, -1632970141, 1682692232, -1891363613, 361435263, -1298758276, 1941575700, 2024042338, -83369850, 1666531826, -478401337, 166809651, -2137403731, 2090270475, 1526275082, -2037877338, -1534621073, 1454689250, 1941975954, 71757581, 1317690060, 62647477, 2018562603, 1645930499, -1195114170, 264950860, 2180, -1947191567, -1947190515, -1947188782, 65012844, 2097230, 65014182, 65014838, -173161891, 2122146, 488601800, 478131912, 2210062, -1531639945, 1757419041, 2342, -71117602, 43163514, -1034806157, 515215048, 2287470, 1949294047, 310477953, -475355116, -1899599486, 2018645, -44281222, 849069497, 1567046969, -1600931301, 2000632667, -1536903235, 2000646121, -1590535212, 1567060423, -681174902, -1468810648, -523935405, -2013470288, 76079, -1204752338, -947445728, 75922139, -1911998296, 841424347, 77388366, 1527579606, -565019437, -565019436, -1854418717, 2014597491, 2030550014, -1477449824, 2116703416, -1477049570, 1456148737, -2103044617, -1652268352, -911026225, 2030566313, 903012212, -1693962467, 1265182974, -645326218, 823454131, -1933087520, 174416446, 789791136, -1217415016, -1306826246, -1729119588, -1306812792, 215032311, 415746375, -202390477, -1873834213, 971478344, 828478987, -806223890, -1143057341, -202159303, 2647074]

osgi.wiring.package;
	bundle-symbolic-name = org.apache.servicemix.bundles.jsch;
	bundle-version = 0.1.55.1;
	osgi.wiring.package = com.jcraft.jsch.jce;
	version = 0.1.55;
	bnd.hashes = [573506460, 573507033, 579792361, 579792934, 604846592, 604847165, -30172584, -1223236385, -1223235333, -759752102, 2180, -1203608207, -1203607155, -1203605422, 65786604, 2221031, 1742301239, -685752940, -1823053428, 392314281, 392315118, 392317873, 2000632667, -1536903235, 2000646121, 76158, 75922139, -1854418717, 2543909, -1850268089, -1850267037, -1850265334, -1306826246, 1636151863, 1636152915, 1636154648, -2063099598, -1306812792, 235061392, 235061965];
	uses := javax.crypto,javax.crypto.spec,com.jcraft.jsch,javax.crypto.interfaces

osgi.wiring.package;
	bundle-symbolic-name = org.apache.servicemix.bundles.jsch;
	bundle-version = 0.1.55.1;
	osgi.wiring.package = com.jcraft.jsch.jcraft;
	version = 0.1.55;
	bnd.hashes = [-1195114170, 2221031, 1742301239, -685752940, -1823053428, 392314281];
	uses := com.jcraft.jzlib,com.jcraft.jsch

osgi.wiring.package;
	bundle-symbolic-name = org.apache.servicemix.bundles.jsch;
	bundle-version = 0.1.55.1;
	osgi.wiring.package = com.jcraft.jsch.jgss;
	version = 0.1.55;
	bnd.hashes = [-723852638];
	uses := org.ietf.jgss,com.jcraft.jsch

Both bundles provide the same package version.
Also no duplicate exporters (see here ) with different hashes as far as I am can see.

image

Question:
I assume this is correct. since both exporting bundles provide the same package and version the resolver can pick one of them.

@pkriens

@pkriens
Copy link
Member Author

pkriens commented Dec 7, 2023

wow, this is shaping up to become a nice tool!

I think is ok. There are a lot of rewrapped jars out there. The resolver will pick them more or less randomly. As long as the contracts are fulfilled this is ok.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants