#!/usr/bin/env python ################################################################################ # # CDDL HEADER START # # The contents of this file are subject to the terms of the Common Development # and Distribution License Version 1.0 (the "License"). # # You can obtain a copy of the license at # http:# www.opensource.org/licenses/CDDL-1.0. See the License for the # specific language governing permissions and limitations under the License. # # When distributing Covered Code, include this CDDL HEADER in each file and # include the License file in a prominent location with the name LICENSE.CDDL. # If applicable, add the following below this CDDL HEADER, with the fields # enclosed by brackets "[]" replaced with your own identifying information: # # Portions Copyright (c) [yyyy] [name of copyright owner]. All rights reserved. # # CDDL HEADER END # # Copyright (c) 2017, Regents of the University of Minnesota. # All rights reserved. # # Contributor(s): # Ellad B. Tadmor # ################################################################################ # The docstring below is vc_description '''Check that the model has no memory leaks. This is tested using the Valgrind memory debugging tool (http://valgrind.org) by performing a series of energy and force calculations on a randomly distorted face-centered cubic (FCC) cube base structure for both non-periodic and periodic boundary conditions. Separate configurations are tested for each species supported by the model, as well as one containing a random distribution of all species. Configurations used for testing are provided as auxiliary files.''' # Python 2-3 compatible code issues from __future__ import print_function try: input = raw_input except NameError: pass import sys import kimvc import runner2 import subprocess import re __version__ = "001" __author__ = "Ellad Tadmor" ################################################################################ # # FUNCTIONS # ################################################################################ ################################################################################ def do_vc(model, vc): ''' Do memory leak check ''' # call the code used to look for memory leaks durectky to generate # the output for the report runner2.memory_leaks_test_process(model, vc) # call memory leaks test process using valigrind to look for leaks try: valgrind_out = subprocess.check_output(['valgrind', '--suppressions=./valgrind-python.supp', 'python', 'runner2.py', model], stderr=subprocess.STDOUT, universal_newlines=True) except: raise kimvc.KIMVCError('failed to run valgrind; check that it is installed.') # print valgrind output to report dashwidth = 80 vc.rwrite('') vc.rwrite('='*dashwidth) vc.rwrite(' '*7 + 'VALGRIND OUTPUT') vc.rwrite('='*dashwidth) vc.rwrite('') vc.rwrite(valgrind_out) vc.rwrite('='*dashwidth) # determine grade vc.rwrite('') vc.rwrite('To pass this verification check the number of bytes that are ' '"definitely lost" ') vc.rwrite('or "indirectly lost" must be zero.') vc.rwrite('') vc.rwrite('NOTE that Valgrind will typically report non-zero ' '"possibly lost" bytes due to') vc.rwrite("Python's internal memory allocation and garbage collection " "that it does not monitor.") vc.rwrite('') definitely_lost = int(re.search('definitely lost: ([0-9]+)', valgrind_out).group(1)) indirectly_lost = int(re.search('indirectly lost: ([0-9]+)', valgrind_out).group(1)) leak_detected = definitely_lost > 0 or indirectly_lost > 0 # Run again and generate full valgrind output in aux file try: valgrind_out = subprocess.check_output(['valgrind', '--leak-check=full', '--show-leak-kinds=all', 'python', 'runner2.py', model], stderr=subprocess.STDOUT, universal_newlines=True) except: raise kimvc.KIMVCError('Failed to run valgrind; check that it is installed.') aux_file = 'valgrind.out' vc.vc_files.append(aux_file) vc.write_aux_string(aux_file, valgrind_out) vc.rwrite('Full Valgrind output written to auxiliary file "{}"'. format(aux_file)) if leak_detected: vc.rwrite('(Search for the word "lost" in the file to identify ' 'memory leaks.)') vc.rwrite('') # report grade if not leak_detected: vc_grade = 'P' vc_comment = 'No memory leak detected.' else: vc_grade = 'F' vc_comment = 'Memory leak detected.' return vc_grade, vc_comment ################################################################################ # # MAIN PROGRAM # ############################################################################### if __name__ == '__main__': vcargs = {"vc_name" : "vc-memory-leak", "vc_author" : __author__, "vc_description" : kimvc.vc_stripall(__doc__), "vc_category" : "informational", "vc_grade_basis" : "passfail", "vc_files" : [], "vc_debug" : False} # Set to True to get exception traceback info # Get the model extended KIM ID: model = input("Model Extended KIM ID = ") # Execute VC kimvc.setup_and_run_vc(do_vc, model, **vcargs)