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

Checking only read permissions when asserting function preconditions #532

Open
wants to merge 7 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion silver
Submodule silver updated 37 files
+11 −4 src/main/scala/viper/silver/ast/Expression.scala
+6 −3 src/main/scala/viper/silver/ast/Program.scala
+2 −0 src/main/scala/viper/silver/ast/pretty/PrettyPrinter.scala
+54 −10 src/main/scala/viper/silver/ast/utility/Consistency.scala
+5 −2 src/main/scala/viper/silver/ast/utility/Expressions.scala
+3 −3 src/main/scala/viper/silver/ast/utility/InverseFunctions.scala
+2 −1 src/main/scala/viper/silver/ast/utility/Nodes.scala
+15 −6 src/main/scala/viper/silver/ast/utility/Permissions.scala
+7 −0 src/main/scala/viper/silver/frontend/SilFrontEndConfig.scala
+8 −2 src/main/scala/viper/silver/frontend/SilFrontend.scala
+7 −2 src/main/scala/viper/silver/parser/FastParser.scala
+8 −1 src/main/scala/viper/silver/parser/ParseAst.scala
+2 −0 src/main/scala/viper/silver/parser/ParseAstKeyword.scala
+5 −4 src/main/scala/viper/silver/parser/Translator.scala
+1 −1 src/main/scala/viper/silver/plugin/standard/predicateinstance/PredicateInstancePlugin.scala
+5 −0 src/main/scala/viper/silver/reporter/Message.scala
+7 −0 src/main/scala/viper/silver/reporter/Reporter.scala
+4 −4 src/main/scala/viper/silver/testing/BackendTypeTest.scala
+2 −2 src/main/scala/viper/silver/verifier/VerificationResult.scala
+38 −0 src/test/resources/all/asserting/function.vpr
+19 −0 src/test/resources/all/asserting/other-fail.vpr
+44 −0 src/test/resources/all/asserting/qp.vpr
+73 −0 src/test/resources/all/asserting/simple-fail.vpr
+22 −0 src/test/resources/all/asserting/trigger.vpr
+17 −0 src/test/resources/all/asserting/wand.vpr
+444 −0 src/test/resources/all/functions/function_precondition_perms.vpr
+8 −8 src/test/resources/all/issues/carbon/0196.vpr
+1 −1 src/test/resources/all/issues/carbon/0223.vpr
+2 −9 src/test/resources/all/issues/silicon/0030.vpr
+5 −5 src/test/resources/all/issues/silicon/0240.vpr
+1 −0 src/test/resources/all/issues/silicon/0376.vpr
+1 −1 src/test/scala/ChopperTests.scala
+4 −4 src/test/scala/ConsistencyTests.scala
+4 −4 src/test/scala/FeatureCombinationsTests.scala
+5 −5 src/test/scala/MethodDependencyTests.scala
+1 −1 src/test/scala/SimplifierTests.scala
+1 −1 src/test/scala/UtilityTests.scala
6 changes: 6 additions & 0 deletions src/main/scala/viper/carbon/CarbonVerifier.scala
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,12 @@ case class CarbonVerifier(override val reporter: Reporter,
}
else false

def respectFunctionPrecPermAmounts: Boolean = if (config != null) config.respectFunctionPrePermAmounts.toOption match {
case Some(b) => b
case None => false
}
else false

override def usePolyMapsInEncoding =
if (config != null) {
config.desugarPolymorphicMaps.toOption match {
Expand Down
4 changes: 4 additions & 0 deletions src/main/scala/viper/carbon/modules/PermModule.scala
Original file line number Diff line number Diff line change
Expand Up @@ -159,4 +159,8 @@ trait PermModule extends Module with CarbonStateComponent {
// removes permission to w#ft (footprint of the magic wand) (See Heap module for w#ft description)
def exhaleWandFt(w: sil.MagicWand): Stmt

def setCheckReadPermissionOnlyState(readOnly: Boolean): Boolean

def assumePermUpperBounds: Stmt

}
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,7 @@ class DefaultExpModule(val verifier: Verifier) extends ExpModule with Definednes
case sil.Unfolding(_, exp) =>
translateExp(exp)
case sil.Applying(_, exp) => translateExp(exp)
case sil.Asserting(_, exp) => translateExp(exp)
case sil.Old(exp) =>
val prevState = stateModule.state
stateModule.replaceState(stateModule.oldState)
Expand Down Expand Up @@ -378,6 +379,13 @@ class DefaultExpModule(val verifier: Verifier) extends ExpModule with Definednes
checkDefinednessImpl(e1, error, makeChecks = makeChecks, definednessStateOpt) :: // short-circuiting evaluation:
If(UnExp(Not, translateExp(e1)), checkDefinednessImpl(e2, error, makeChecks = makeChecks, definednessStateOpt), Statements.EmptyStmt) ::
Nil
case sil.Asserting(assertion, e) =>
val checkAssDefined = checkDefinedness(assertion, error, makeChecks = makeChecks)
val (stateStmt, state) = stateModule.freshTempState("asserting")
val checkAssHolds = MaybeComment("Exhale assertion of asserting", exhale(Seq((assertion, error, Some(error)))))
stateModule.replaceState(state)
val checkEDefined = checkDefinedness(e, error, makeChecks = makeChecks)
checkAssDefined :: stateStmt :: checkAssHolds :: checkEDefined :: Nil
case [email protected](_, _) =>
checkDefinednessWand(w, error, makeChecks = makeChecks)
case sil.Let(v, e, body) =>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -190,6 +190,8 @@ with DefinednessComponent with ExhaleComponent with InhaleComponent {
override def translateFunction(f: sil.Function, names: Option[mutable.Map[String, String]]): Seq[Decl] = {
env = Environment(verifier, f)
ErrorMemberMapping.currentMember = f

val oldPermOnlyState = permModule.setCheckReadPermissionOnlyState(!verifier.respectFunctionPrecPermAmounts)
val res = MaybeCommentedDecl(s"Translation of function ${f.name}",
MaybeCommentedDecl("Uninterpreted function definitions", functionDefinitions(f), size = 1) ++
(if (f.isAbstract) Nil else
Expand All @@ -207,6 +209,7 @@ with DefinednessComponent with ExhaleComponent with InhaleComponent {
names.get ++= usedNames
}

permModule.setCheckReadPermissionOnlyState(oldPermOnlyState)
env = null
ErrorMemberMapping.currentMember = null
res
Expand Down Expand Up @@ -665,7 +668,7 @@ with DefinednessComponent with ExhaleComponent with InhaleComponent {

val args = p.formalArgs map translateLocalVarDecl
val init : Stmt = MaybeCommentBlock("Initializing the state",
stateModule.initBoogieState ++ assumeAllFunctionDefinitions ++ (p.formalArgs map (a => allAssumptionsAboutValue(a.typ,mainModule.translateLocalVarDecl(a),true)))
stateModule.initBoogieState ++ assumeAllFunctionDefinitions ++ permModule.assumePermUpperBounds ++ (p.formalArgs map (a => allAssumptionsAboutValue(a.typ,mainModule.translateLocalVarDecl(a),true)))
)

val predicateBody = p.body.get
Expand Down Expand Up @@ -871,12 +874,17 @@ with DefinednessComponent with ExhaleComponent with InhaleComponent {
* contain permission introspection.
*/
val curState = stateModule.state
val oldReadState = permModule.setCheckReadPermissionOnlyState(true)
defState.setDefState()
val res = executeExhale()
permModule.setCheckReadPermissionOnlyState(oldReadState)
stateModule.replaceState(curState)
res
case None =>
executeExhale()
val oldReadState = permModule.setCheckReadPermissionOnlyState(true)
val res = executeExhale()
permModule.setCheckReadPermissionOnlyState(oldReadState)
res
}
}
) ++
Expand Down Expand Up @@ -961,7 +969,7 @@ with DefinednessComponent with ExhaleComponent with InhaleComponent {
wandModule.translatingStmtsInWandInit()
}
(checkDefinedness(acc, errors.FoldFailed(fold), insidePackageStmt = insidePackageStmt) ++
checkDefinedness(perm, errors.FoldFailed(fold), insidePackageStmt = insidePackageStmt) ++
checkDefinedness(perm.getOrElse(sil.FullPerm()()), errors.FoldFailed(fold), insidePackageStmt = insidePackageStmt) ++
foldFirst, foldLast)
}
}
Expand Down Expand Up @@ -998,7 +1006,7 @@ with DefinednessComponent with ExhaleComponent with InhaleComponent {
unfold match {
case sil.Unfold([email protected]([email protected](_, _), perm)) =>
checkDefinedness(acc, errors.UnfoldFailed(unfold), insidePackageStmt = insidePackageStmt) ++
checkDefinedness(perm, errors.UnfoldFailed(unfold)) ++
checkDefinedness(perm.getOrElse(sil.FullPerm()()), errors.UnfoldFailed(unfold)) ++
unfoldPredicate(acc, errors.UnfoldFailed(unfold), false, statesStackForPackageStmt, insidePackageStmt)
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -137,7 +137,7 @@ class DefaultMainModule(val verifier: Verifier) extends MainModule with Stateles
val initOldStateComment = "Initializing of old state"
val ins: Seq[LocalVarDecl] = formalArgs map translateLocalVarDecl
val outs: Seq[LocalVarDecl] = formalReturns map translateLocalVarDecl
val init = MaybeCommentBlock("Initializing the state", stateModule.initBoogieState ++ assumeAllFunctionDefinitions ++ stmtModule.initStmt(method.bodyOrAssumeFalse))
val init = MaybeCommentBlock("Initializing the state", stateModule.initBoogieState ++ assumeAllFunctionDefinitions ++ permModule.assumePermUpperBounds ++ stmtModule.initStmt(method.bodyOrAssumeFalse))
val initOld = MaybeCommentBlock("Initializing the old state", stateModule.initOldState)
val paramAssumptions = mWithLoopInfo.formalArgs map (a => allAssumptionsAboutValue(a.typ, translateLocalVarDecl(a), true))
val inhalePre = translateMethodDeclPre(pres)
Expand Down Expand Up @@ -269,9 +269,9 @@ class DefaultMainModule(val verifier: Verifier) extends MainModule with Stateles
val resourceCurPerm =
q.exp match {
case r : sil.FieldAccess =>
sil.FieldAccessPredicate(r, curPermVar)()
sil.FieldAccessPredicate(r, Some(curPermVar))()
case r: sil.PredicateAccess =>
sil.PredicateAccessPredicate(r, curPermVar)()
sil.PredicateAccessPredicate(r, Some(curPermVar))()
case _ => sys.error("Not supported resource in quasihavoc")
}

Expand Down
Loading
Loading