Formales Ausführungsmodell für Java (oder allgemeine imperative Sprache)


7

Ich versuche, einige Aussagen über die Ausführung in Java-Programmen unter einigen starken Einschränkungen zu beweisen (im Grunde genommen habe ich die Vermutung, dass zwei Methoden, die eine Reihe von Einschränkungen für eine bestimmte Eingabe erfüllen, äquivalent sind - dh den Wert und den Status danach zurückgeben Ausführung sind identisch). Um dies zu beweisen, suche ich nach einer Art Formalismus, der mich darüber sprechen lässt.

Ich bin mit der operativen Semantik funktionaler Sprachen vertraut und könnte möglicherweise für Schleifen / while-Schleifen in rekursive Funktionen übersetzen ... Ich würde dies lieber nicht tun, und es wäre schön, einige Maschinen zu haben, damit ich im imperativen Land bleiben kann .

Insbesondere möchte ich über den Zustand einer Methode im k- ten Ausführungsschritt nachdenken. Dies beinhaltet den globalen Zustand:

  • Aufrufe wie this.field = 2aktualisieren unseren Klassenstatus
  • Aufrufe zur Änderung des Aktualisierungsstatus von Parametern außerhalb unserer Methode:
    • myParam.setFoo(...)
    • myParam.x = y
  • Aufruf statischer Methoden
    • Blah.static_side_effects()

Ich gehe davon aus, dass dies alles deterministisch ist . Das heißt, ich möchte die Annahme formalisieren, dass, wenn eine dieser globalen Statusaktualisierungen in zwei Methoden erfolgt, deren globaler und lokaler Ausführungsstatus identisch sind, der neue Status ebenfalls identisch ist - dass jeder Berechnungsschritt bestimmt wird genau nach globalem Staat und lokalem Staat. Dies schließt offensichtlich RNGs und Parallelität aus (aber ich kann später darauf eingehen ...).

Irgendwelche Ideen oder Quellen, wie ich das angehen könnte? Mein einziger Gedanke ist, Methoden als Liste von Anweisungen zu behandeln und zu versuchen, eine Anweisungssemantik formal zu beschreiben.

Wenn möglich, würde ich dies gerne auf Java-Sprachebene und nicht auf JVM-Ebene tun. Dies ist möglicherweise nicht machbar, aber mein Ziel ist es, vorerst einige vernünftige Annahmen über meine operative Semantik zu treffen und diese dann von dort zu übernehmen.

Oh, eine letzte Anmerkung - alle Vorschläge, wie ich diese Frage verbessern kann, wären sehr dankbar. Ich versuche, die richtige Sprache zu finden, um die Frage zu stellen, und wenn ich Terminologie missbrauche (wie den lokalen / globalen Ausführungsstatus ...), würde ich dies gerne korrigieren.


3
Vielleicht sind die Artikel über "Featherweight Java" relevant. Es ist schon eine Weile her, dass ich etwas darüber gelesen habe, aber sie haben versucht, eine relativ kleine Java-Teilmenge zu definieren, die immer noch allgemein genug ist und eine anständige Semantik zulässt. Dies für volles Java zu tun ist übertrieben: Die offizielle Sprachspezifikation umfasst 700 Seiten mit informellen Beschreibungen, IIRC.
Chi

Ja, ich habe mir die technischen Daten einmal angesehen und bin weitergegangen. Auch das sind nur die Sprachspezifikationen IIR - die JVM-Spezifikationen haben weitere 600-700 Seiten. Ich werde mich jedoch mit Featherweight Java befassen. Vielen Dank für den Vorschlag
Ben Kushigian

Oh wow, Pierce und Wadler! Ich werde dies unabhängig von seiner Anwendbarkeit auf meine Arbeit lesen: D
Ben Kushigian

Antworten:


7

Featherweight Java wird in der PL-Community sehr geschätzt. Wenn dies jedoch nicht Ihren Anforderungen entspricht, finden Sie hier einen allgemeinen Ansatz für die Modellierung:

  • Formalisieren Sie den AST Ihrer Sprache in Ausdrücke und Aussagen
  • Schreiben Sie eine Semantik für Ausdrücke und Anweisungen. Ihre Semantik benötigt:
    • eine Bewertungsbeziehung, die Ausdruckszustandspaare in Beziehung setzt (e,σ) zu einem ausgewerteten Ausdruck mit aktualisiertem Status (e,σ),
    • eine Ausführungsbeziehung, die Anweisungs-Status-Paare in Beziehung setzt (s,σ) Zustände ausgeben σ.
  • Diese sind gegenseitig rekursiv und können je nach Bedarf eine große oder kleine Semantik sein. Ein großer Schritt ist einfacher, aber schlechter bei der Modellierung nicht terminierender Ausführungen.

Diese Grundstruktur bringt Sie ziemlich weit. Um Java zu modellieren, möchten Sie Ihren Statussatz wahrscheinlich hierarchisch um bestimmte Objekte herum strukturieren, aber die Grundprinzipien sind dieselben. Sie möchten auch den dynamischen Versand modellieren, daher ist es wahrscheinlich sinnvoll, Klassenmethoden in Funktionen umzuwandeln, die ein explizites "this" -Argument verwenden.

Eine axiomatische Semantik, dh Hoare-Tripel, die eine Logik von Vor- und Nachbedingungen für Anweisungen zur Modellierung imperativer Programme definieren. Ich weiß nicht, wie diese mit OOP zusammenhängen, aber ich bin sicher, dass jemand in den 50 Jahren, in denen er da war, es versucht hat.

Sie könnten auch an Software Foundations interessiert sein . Es orientiert sich an der Argumentation über imperative Sprachen im Coq-Theorembeweiser, bietet jedoch einen hervorragenden Überblick über die formale Semantik.


Die ursprüngliche Hoare-Tripel / axiomatische Semantik behandelte keine Konstrukte höherer Ordnung wie erstklassige Funktionen und Objekte. Moderne Ansätze wie die Logik gebündelter Implikationen, insbesondere in Form von Trennungslogik, und die Hoare-Typentheorie bieten einen Ansatz, der solche Merkmale handhaben kann.
Derek Elkins verließ SE

8

Es gibt eine (betriebliche) Semantik für Java 1.4, die in derKRahmen . Diesem Framework ist ein Proofsystem namens Matching Logic zugeordnet . Während diese Seite eine Prototyp-Implementierung beschreibt, scheint es, dass die Funktionalität in die integriert wirdKFramework-Tools selbst als kprover. Leider scheint das Framework gerade aktualisiert zu werden, und es ist ein bisschen mühsam, das Framework zum Erstellen und Arbeiten zu bringen, und ich bin mir nicht sicher, wie praktisch und / oder funktional es kproverderzeit ist. Sie können jedoch manuell Dinge beweisen, die auf die Betriebssemantik verweisen (und auf Wunsch auch das Matching Logic-Proof-System verwenden). Das Dokument zur Beschreibung der Java-Semantik, K-Java: Eine vollständige Semantik von Java , verweist auf einige andere Systeme, die weniger vollständig sind, aber für Ihre Zwecke möglicherweise vollständig genug sind. Das heißt, sie sind möglicherweise nicht darauf ausgerichtet, Eigenschaften von Java-Programmen zu beweisen. In der Tat wird die Semantik in der Arbeit eher zur Modellprüfung als zur Überprüfung der Korrektheit verwendet.

Dies ist eine Antwort, wenn Sie ein hohes Maß an Sicherheit wünschen, dass sich der tatsächliche Java-Code so verhält, wie Sie es beabsichtigen. Wenn das Ziel darin besteht, den Algorithmus mehr zu verifizieren als die spezifische Realisierung in Java, ist dies wahrscheinlich ein Overkill. Das heißt, Sie könnten leicht eine einfache imperative Sprache in formalisierenKwenn Sie nur grundlegende Imperativ- / OO-Funktionen benötigen. Dies geschieht in der Tat als Übung in derKFramework-Tutorial. Wenn Sie Ihr Problem in das Fragment von C umformulieren können, das der Matching Logic-Prototyp unterstützt, können Sie es möglicherweise so verwenden, wie es ist.

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.