Contract Programming For C++0x

Similar documents
Assertions, pre/postconditions

UC Santa Barbara. CS189A - Capstone. Christopher Kruegel Department of Computer Science UC Santa Barbara

CS 161 Computer Security

Advanced Systems Programming

G Programming Languages - Fall 2012

Short Notes of CS201

CS201 - Introduction to Programming Glossary By

Method Description for Semla A Software Design Method with a Focus on Semantics

A Standard flat_map. 1 Revisions. 2 Introduction. 3 Motivation and Scope. 1.1 Changes from R Changes from R0

COL728 Minor2 Exam Compiler Design Sem II, Answer all 5 questions Max. Marks: 20

by Pearson Education, Inc. All Rights Reserved. 2

September 10,

17. Assertions. Outline. Built-in tests. Built-in tests 3/29/11. Jelle Slowack, Bart Smets, Glenn Van Loon, Tom Verheyen

C++11: 10 Features You Should be Using. Gordon R&D Runtime Engineer Codeplay Software Ltd.

AIMS Embedded Systems Programming MT 2017

17. Assertions. Jelle Slowack, Bart Smets, Glenn Van Loon, Tom Verheyen

CSCI-1200 Data Structures Spring 2018 Lecture 8 Templated Classes & Vector Implementation

Fast Introduction to Object Oriented Programming and C++

Absolute C++ Walter Savitch

Advanced Programming in C++ Container Design I

What will happen if we try to compile, link and run this program? Do you have any comments to the code?

Contracts programming for C++20

2 ADT Programming User-defined abstract data types

Contracts programming for C++20

Data Structures and Algorithms for Engineers

Appendix. Grammar. A.1 Introduction. A.2 Keywords. There is no worse danger for a teacher than to teach words instead of things.

G Programming Languages Spring 2010 Lecture 4. Robert Grimm, New York University

Objects Managing a Resource

class Polynomial { public: Polynomial(const string& N = "no name", const vector<int>& C = vector<int>());... };

Software Engineering Concepts: Invariants Silently Written & Called Functions Simple Class Example

CSE409, Rob Johnson, Alin Tomescu, November 11 th, 2011 Buffer overflow defenses

Exception Safety. CS 311 Data Structures and Algorithms Lecture Slides Wednesday, October 28, Glenn G. Chappell. continued

Lecture Notes on Queues

Allocation & Efficiency Generic Containers Notes on Assignment 5

Programming in C and C++

COMP322 - Introduction to C++ Lecture 02 - Basics of C++

Improving improved shared_ptr. 1.Overview. 2.Motivation. 3.Proposed text [util.smartptr.shared]

A Standard flat_set. This paper outlines what a (mostly) API-compatible, non-node-based set might look like.

struct _Rational { int64_t Top; // numerator int64_t Bottom; // denominator }; typedef struct _Rational Rational;

Lecture 10 Notes Linked Lists

Variables. Data Types.

Introduction to Computers and C++ Programming p. 1 Computer Systems p. 2 Hardware p. 2 Software p. 7 High-Level Languages p. 8 Compilers p.

AXIOMS OF AN IMPERATIVE LANGUAGE PARTIAL CORRECTNESS WEAK AND STRONG CONDITIONS. THE AXIOM FOR nop

Semantic Analysis. CSE 307 Principles of Programming Languages Stony Brook University

Exception Namespaces C Interoperability Templates. More C++ David Chisnall. March 17, 2011

The pre-processor (cpp for C-Pre-Processor). Treats all # s. 2 The compiler itself (cc1) this one reads text without any #include s

Lecture 10 Notes Linked Lists

Learning Objectives. C++ For Artists 2003 Rick Miller All Rights Reserved xli

G52CPP C++ Programming Lecture 13

C++: Const Function Overloading Constructors and Destructors Enumerations Assertions

CSE 303: Concepts and Tools for Software Development

Lecture Notes on Memory Layout

Bruce Merry. IOI Training Dec 2013

Introduction to Linked Lists. Introduction to Recursion Search Algorithms CS 311 Data Structures and Algorithms

Type Hierarchy. Comp-303 : Programming Techniques Lecture 9. Alexandre Denault Computer Science McGill University Winter 2004

CSE 374 Programming Concepts & Tools. Hal Perkins Spring 2010

QUIZ. What are 3 differences between C and C++ const variables?

C Programming Review CSC 4320/6320

CSE 331 Final Exam 3/16/15 Sample Solution

Problem Solving with C++

n Specifying what each method does q Specify it in a comment before method's header n Precondition q Caller obligation n Postcondition

double d0, d1, d2, d3; double * dp = new double[4]; double da[4];

Basic Array Implementation Exception Safety

Program Verification (6EC version only)

Midterm I Exam Principles of Imperative Computation Frank Pfenning. February 17, 2011

Ch. 12: Operator Overloading

Lecture 8. Xiaoguang Wang. February 13th, 2014 STAT 598W. (STAT 598W) Lecture 8 1 / 47

Exploring the design space of contract specifications for C++

References: internet notes; Bertrand Meyer, Object-Oriented Software Construction; 10/14/2004 1

CSCI-1200 Data Structures Fall 2018 Lecture 7 Templated Classes & Vector Implementation

Proposal to add Design by Contract to C++

Instantiation of Template class

Practical C++ Programming

Extending Classes (contd.) (Chapter 15) Questions:

CS201 Some Important Definitions

Design Principles for a Beginning Programming Language

Simplifying C++0x Concepts

Lecture 15: Even more pointer stuff Virtual function table

CS3157: Advanced Programming. Outline

Lecture Notes on Contracts

Programming with Haiku

COS 320. Compiling Techniques

Topics Covered Thus Far. CMSC 330: Organization of Programming Languages. Language Features Covered Thus Far. Programming Languages Revisited

Simple Contracts for C++ (R1)

Code Contracts in C#

Assertions. Assertions - Example

G52CPP C++ Programming Lecture 12

Lecture 2 Polymorphism, Traits, Policies, and Inheritance

III. Classes (Chap. 3)

18-642: Code Style for Compilers

hwu-logo.png 1 class Rational { 2 int numerator ; int denominator ; 4 public Rational ( int numerator, int denominator ) {

Semantic Analysis. Lecture 9. February 7, 2018

Arrays. Returning arrays Pointers Dynamic arrays Smart pointers Vectors

CSE 333 Midterm Exam 2/14/14

C++_ MARKS 40 MIN

COEN244: Class & function templates

Outline. iterator review iterator implementation the Java foreach statement testing

CS 315 Software Design Homework 3 Preconditions, Postconditions, Invariants Due: Sept. 29, 11:30 PM

Sets and MultiSets. Contents. Steven J. Zeil. July 19, Overview of Sets and Maps 4

1c) (iv) and (v) OR (v) only (hindsight showed that the question was more ambiguous than intended)

Transcription:

Contract Programming For C++0x WG21/N1800 and J16/05-0060 Lawrence Crowl and Thorsten Ottosen lawrence.crowl@sun.com and nesotto@cs.aau.dk 2005-04-27

Overview This is an annotated version of the presentation given before the EWG in Lillehammer. All comments are specified with italics. In general comments to a page are put on the following page. The details of the proposal may be found in N1773.

Essentials The idea is to extend function declarations with pre- and post-conditions class declarations with class invariants namespace declarations with namespace invariants Notice that contracts are put on declarations and not on definitions. This is essential if the compiler is to take optimal advantage of the contracts. Postcondition and invariants are only meant to be executed in debug-builds whereas it might be feasible to include some or all precondition checks. The precondition can be generated at the call-site so the error is correctly reported in the caller and not in the callee.

Pre- and postconditions Example: vector<t>::push_back()/begin() void push_back( const T& val ) precondition size() < max_size(); postcondition back() == val; size() == old size() + 1; capacity() >= old capacity(); iterator begin() postcondition( result ) if( empty() ) result == end();

Pre- and postconditions (comments) So this is how pre- and postconditions look like. In the postcondition of push_back(), the keyword old is applied to an expression; the meaning is to take a copy of the expression before entering the function body and then compare it with something in the postcondition. Obviously a better keyword than old must be found. In the postcondition of begin() we see how we can get a const reference to the return value of the function, here we name it result. This construct makes it easier to specify postconditions for function with multiple exists. Also note how we may embed if-statements in the contracts. Postconditions will disable contracts when calling other functions to avoid problems with infinite recursion.

Example: vector<t> invariant Class invariants static invariant is_assignable<t>::value : "value_type must be Assignable" ; is_copy_constructible<t>::value : "value_type must be CopyConstructible" ; invariant ( size() == 0 ) == empty(); size() == std::distance( begin(), end() ); size() == std::distance( rbegin(), rend() ); size() <= capacity(); capacity() <= max_size();

Class invariants (comments) The first invariant is evaluated at compile-time like the proposed static_assert(). The intend is that the comment is printed by the compiler on failure. The second invariant is evaluated at runtime in debug builds. Calls to the invariant will be generated at the end of the constructor body and before calls to pre- and postconditions on public functions. This order is necessary since pre- and postconditions might rely on a valid object.

Example: namespace invariant Namespace invariants namespace foo int buffer_size; int* buffer; invariant buffer_size > 0; buffer!= 0; static invariant sizeof( int ) >= 4 : "int must be 32 bit";

Motivation (1) Minimize the need for separate documentation and implementation Any kind of redundancy eventually leads to code and documentation being out of sync Natural language is remarkably bad for precise statements So remove redundancy by turning comments into code /** * Removes the last element of the container. * It is required that such an element exists. */ void pop_back(); void pop_back() precondition not empty(); postcondition size() == old size() - 1;

void bar( int* p ) precondition p!= NULL;... foo_bar(p); Motivation (2) It can enable the compiler to generate faster code If the compiler can determine the precondition is fulfilled, the call to the precondition can be removed The compiler can assume all contracts are true in the body of functions void foo( int i ) precondition i % 2 == 0;... i /= 2; // safe to do i»= 1 inline void foo_bar( int* p )... if( p )...

Motivation (2) (comments) The compiler can always assume preconditions and invariants to be true before compiling the body of a function; and similar, it can always assume postconditions and invariants to be true after a function call. In the function foo() the precondition enables the compiler to optimize a division; this optimization would not have been possible without the precondition because i might be a negative number. When inlining foo_bar() inside bar() the compiler can propagate the precondition of bar() to perform dead-code elimination.

Motivation (3) Improves communication between designers and programmers in large projects (Jack Reeves argued that was a major reason for C++ s success in the 90 s) Inheritance is easier to use correctly (pre- and postconditions inherited) Improve C++ s role in programming courses (teachers will love this) It might make static analysis tools more powerful It will benefit C++ s image as a secure language It gives us a safer library for use in teaching C++ T operator[]( size_type off ) precondition off < size();

Motivation (3) (comments) Sometimes it is OK to make virtual functions public or protected; pre- and postconditions will be "inherited" so when the programmer override the virtual function, he does not need to repeat these. Security is becoming a bigger and bigger issue. The C committee are working on a new version of the C library which is less prone to buffer overruns. In C++ we should strive for more general approaches to security instead of just fixing a particular library function. Teachers and C++ committee members often ask for a more secure version of the standard library for use in programming courses. If we apply contracts to the standard library, we can check many common errors like out-of-range in the subscript operator.

Complements concepts well Motivation (4) template< class T > concept EqualityComparable bool operator==( T l, T r ) postcondition( result ) result ==!( l!= r ); ; bool operator!=( T l, T r ) postcondition( result ) result ==!( l == r ); Benefit: you only specify the contracts once

Motivation (4) (comments) The concepts proposals deal exclusively with structure and types. A concept in the real world has both syntax and semantics using Contract Programming we can attach semantics to our concept. Remark: recall that the postcondition will disable all contracts to avoid infinite recursion. As an example, imagine we could put contracts on a Container concept. Then we did not have to specify the contracts on the N implementations of this concept, but only once in the concept definition itself.

Observations The suggested syntax should allow minimal changes to existing parsers We have some implementation experience (Digital Mars C++, D) = fairly easy to implement (3 man-months) Will require ways to disable run-time checks void critical_for_performance()...!precondition // preconditions disabled here (remark: not part of proposal yet)

Elements of runtime assertions If an assertion is violated at runtime, terminate() is called, but behavior may be customized typedef void (*broken_contract_handler)(); broken_contract_handler set_precondition_broken_handler( broken_contract_handler r ) throw(); Calling a function inside contract scope is subject to the same requirements as a call inside a const member function = prohibits accidental side-effects

Elements of runtime assertions (comments) The fact that you cannot call non-const member functions within contracts in member functions will prevent some accidental side-effects. Moreover, because the compiler knows that contract scope is special, it can utter warnings when it detects a side-effect inside a contract. This is a major benefit compared a library solution, because inside the function body, the compiler cannot say side-effects should not happen.

Function pointers Indirect calls via function pointers will check pre- and post-conditions How? step 1: generate function with two entry points entry 1: at the beginning of the precondition entry 2: after the precondition and before function body step 2: a function pointer would point to entry 1 a normal function call might dispatch to entry 1 or 2 (it depends)

Subcontracting Pre- and postconditions are inherited on virtual functions struct Computation virtual int compute( int r ) const = 0 precondition r > 0; postcondition( result ) result > 0; ; struct MyComputation : public Computation virtual int compute( int r ) const return (int)std::sqrt( float(r) ); ;

Subcontracting (comments) In this example, the programmer does not need to repeat the pre- and postconditions when he override the function. So there is no way sub classes can escape the contract of the base class. The declaration in a sub class can add to the postcondition to make it stronger; we could also allow weaker preconditions, but good examples of that put to use are rare and the misuses many.

Summary Fits many strategic goals of C++ Performance Teaching programming Security Other benefits Makes comments into code and removes redundancy Complements Concepts Emphasize C++ as a language with design in interfaces Fairly easy to implement

Summary (comments) It is worth noticing that something that makes C++ stand out from other languages is that we can distinguish interfaces from implementations; the interface goes in the header file and documents the design of our classes. This is major benefit of C++. Nevertheless many people do not like this aspect of C++; we need to give those people more rewards for writing a separate declaration and Contract Programming is a big step in that direction.