def test_read_geometry(self): """Test open_rmf handling of RMF geometry""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() sf = RMF.SegmentFactory(r) s = sf.get(rn.add_child("test segment", RMF.GEOMETRY)) s.set_coordinates_list([RMF.Vector3(0, 0, 0), RMF.Vector3(5, 5, 5)]) s = sf.get(rn.add_child("test segment2", RMF.GEOMETRY)) s.set_coordinates_list([RMF.Vector3(0, 0, 0), RMF.Vector3(5, 5, 5)]) # Segments are ignored unless they contain two points s = sf.get(rn.add_child("test segment2", RMF.GEOMETRY)) s.set_coordinates_list([RMF.Vector3(0, 0, 0), RMF.Vector3(5, 5, 5), RMF.Vector3(10, 10, 10)]) # Lines with zero length are ignored s = sf.get(rn.add_child("null segment", RMF.GEOMETRY)) s.set_coordinates_list([RMF.Vector3(0, 0, 0), RMF.Vector3(0, 0, 0)]) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) # Two shapes should have been added shapes = structures[0]._drawing._drawing._shapes self.assertEqual(len(shapes), 2)
def replay_error_trace(verifier_output, args): if args.verifier != 'corral': print "Replay for verifiers other than 'corral' currently unsupported; skipping replay" return print "Attempting to replay error trace." missing_definitions = detect_missing_definitions(args.bc_file) if '__SMACK_code' in missing_definitions: print "warning: inline Boogie code found; replay may fail" arguments, return_values = extract_values(verifier_output) with open(args.replay_harness, 'w') as f: f.write(harness(arguments, return_values, missing_definitions)) print "Generated replay harness:", args.replay_harness stubs_bc = temporary_file('stubs', '.bc', args) try_command(['clang', '-c', '-emit-llvm', '-o', stubs_bc, args.replay_harness]) try_command(['clang', '-Wl,-e,_smack_replay_main', '-o', args.replay_exe_file, args.bc_file, stubs_bc]) print "Generated replay executable:", args.replay_exe_file try: if 'error reached!' in try_command(["./" + args.replay_exe_file]): print "Error-trace replay successful." return True else: print "Error-trace replay failed." except Exception as err: print "Error-trace replay caught", err.message return False
def test_command_13(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command13(file_) for key in sorted(found.keys()): print(key, found[key]) for row in EXCLUDE_ROWS: assert row not in found assert "Empty segments are not allowed" in found[32] assert "Empty segments are not allowed" in found[33] assert "Empty segments are not allowed" in found[35] assert "Turn out of sync" in found[37] assert "Empty segments are not allowed" in found[38] assert "Turn out of sync" in found[40] assert "Empty segments are not allowed" in found[41] assert "Turn out of sync" in found[52] assert "Empty segments are not allowed" in found[55] assert "Empty segments are not allowed" in found[58] assert "Turn out of sync" in found[61] assert "Turn out of sync" in found[65] assert "Segment out of sync" in found[66] assert "Turn out of sync" in found[69] assert "Segment out of sync" in found[70] assert "Segment out of sync" in found[74] assert "Turn out of sync" in found[77] assert "Segment out of sync" in found[80] assert "Turn out of sync" in found[83] assert "Segment out of sync" in found[92] assert "Segment out of sync" in found[94]
def fortran_compile_to_bc(input_file, compile_command, args): """Compile a FORTRAN source file to LLVM IR.""" # This method only exists as a hack to get flang to work # with SMACK. When we update to the latest flang on LLVM 5, # this method will no longer be necessary. The hack is # self-contained in this method. # The Debug Info Version in flang is incompatible with # the version that clang uses. The workaround is to use # sed to change the file so llvm-link gives a warning # and not an error. # compile to human-readable format in order to tweak the IR compile_command[1] = '-S' ll = temporary_file( os.path.splitext(os.path.basename(input_file))[0], '.ll', args) try_command(compile_command + ['-o', ll, input_file], console=True) # change the throw level of 'Debug Info Version' from error to warning in the IR try_command([ 'sed', '-i', 's/i32 1, !\"Debug Info Version\"/i32 2, !\"Debug Info Version\"/g', ll ]) try_command(['llvm-as', ll]) try_command(['rm', ll]) bc = '.'.join(ll.split('.')[:-1] + ['bc']) return bc
def test_command_26(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command26(file_) for key in sorted(found.keys()): print(key, found[key]) assert found.pop('warning_message', None) is None
def test_provenance(self): """Test open_rmf handling of RMF provenance""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() strucpf = RMF.StructureProvenanceFactory(r) samplepf = RMF.SampleProvenanceFactory(r) scriptpf = RMF.ScriptProvenanceFactory(r) softwarepf = RMF.SoftwareProvenanceFactory(r) n = rn.add_child("struc", RMF.PROVENANCE) p = strucpf.get(n) p.set_chain('A') p.set_residue_offset(42) p.set_filename('xyz') n = n.add_child("sample", RMF.PROVENANCE) p = samplepf.get(n) p.set_frames(100) p.set_iterations(10) p.set_method('Monte Carlo') p.set_replicas(8) n = n.add_child("script", RMF.PROVENANCE) p = scriptpf.get(n) p.set_filename('abc') n = rn.add_child("software", RMF.PROVENANCE) p = softwarepf.get(n) p.set_location('testurl') p.set_name('testsoftware') p.set_version('1.2.3') n = rn.add_child("misc", RMF.PROVENANCE) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) p1, p2, p3 = structures[0].rmf_provenance self.assertEqual(p1.name, 'Chain A from xyz') self.assertEqual( p2.name, 'Using software testsoftware version 1.2.3 from testurl') self.assertEqual(p3.name, 'misc') self.assertIsNone(p2.previous) prev = p1.previous self.assertEqual( prev.name, 'Sampling using Monte Carlo making 100 frames') prev = prev.previous self.assertIn('Using script', prev.name) self.assertIsNone(prev.previous) self.assertIsInstance(p3, src.io._RMFProvenance)
def test_command4(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command4(file_) keys = sorted(found.keys()) print(len(keys)) for key in keys: print(key, found[key]) assert 0 in found assert 1 not in found assert 2 in found assert not 3 in found assert 4 in found assert 5 in found assert 6 in found assert 7 in found assert 8 in found assert not 9 in found assert 10 in found assert 11 in found assert 12 in found assert 13 in found assert 14 in found assert 15 in found assert 16 in found assert 17 in found assert 18 in found assert 19 in found assert 20 in found assert not 21 in found assert not 22 in found assert not 23 in found assert not 24 in found assert not 25 in found assert not 26 in found assert 27 in found assert 28 in found assert not 29 in found assert 30 in found assert 31 not in found assert 32 not in found assert 33 not in found assert 34 not in found assert 35 not in found assert 36 not in found assert 37 not in found assert 38 not in found assert 39 not in found assert 40 in found assert 41 in found assert 42 in found assert 43 in found assert 44 in found assert 45 in found
def test_command_3(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command3(file_) for key in sorted(found.keys()): print(key, found[key]) for item in EXCLUDES: assert item not in found for item in CATCHES: assert item in found
def test_command_20(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command20(file_) for key in sorted(found.keys()): print(key, found[key]) for row in EXCLUDE: assert row not in found for row in CATCH: assert row in found
def test_alternatives(self): """Test readtraj handling of RMF alternatives""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() af = RMF.AlternativesFactory(r) pf = RMF.ParticleFactory(r) gf = RMF.GaussianParticleFactory(r) n = rn.add_child("topp1", RMF.REPRESENTATION) p = n.add_child("p1", RMF.REPRESENTATION) b = pf.get(p) b.set_mass(1) b.set_radius(4) b.set_coordinates(RMF.Vector3(4., 5., 6.)) a = af.get(n) root = r.add_node("topp2", RMF.REPRESENTATION) p = root.add_child("p2", RMF.REPRESENTATION) b = pf.get(p) b.set_mass(1) b.set_radius(4) b.set_coordinates(RMF.Vector3(4., 5., 6.)) a.add_alternative(root, RMF.PARTICLE) root = r.add_node("topg1", RMF.REPRESENTATION) g = root.add_child("g1", RMF.REPRESENTATION) b = gf.get(g) b.set_variances(RMF.Vector3(1., 1., 1.)) b.set_mass(1.) b = pf.get(g) b.set_radius(4) b.set_coordinates(RMF.Vector3(4., 5., 6.)) a.add_alternative(root, RMF.GAUSSIAN_PARTICLE) r.add_frame("f1", RMF.FRAME) r.add_frame("f2", RMF.FRAME) r.add_frame("f3", RMF.FRAME) r.add_frame("f4", RMF.FRAME) r.add_frame("f5", RMF.FRAME) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() mock_session.logger = MockLogger() structures, status = src.io.open_rmf(mock_session, fname) state = structures[0].child_models()[0] # Just one frame to start with self.assertEqual(list(state.coordset_ids), [1]) src.cmd.readtraj(mock_session, state, first=2, step=2) # Two frames (f2, f4) should have been read self.assertEqual(list(state.coordset_ids), [1, 3, 5])
def test_command_7(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command7(file_) keys = sorted(found.keys()) for key in keys: print(key, found[key]) for key in EXCLUDE: assert key not in found for key in CATCH: assert key in found
def test_read_features(self): """Test open_rmf handling of RMF features""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() rf = RMF.RepresentationFactory(r) bf = RMF.BallFactory(r) n1 = rn.add_child("ball1", RMF.GEOMETRY) b1 = bf.get(n1) b1.set_radius(6) b1.set_coordinates(RMF.Vector3(1., 2., 3.)) n2 = rn.add_child("ball2", RMF.GEOMETRY) b2 = bf.get(n2) b2.set_radius(6) b2.set_coordinates(RMF.Vector3(4., 5., 6.)) n3 = rn.add_child("ball3", RMF.GEOMETRY) b3 = bf.get(n3) b3.set_radius(6) b3.set_coordinates(RMF.Vector3(7., 8., 9.)) n = rn.add_child("feat 1", RMF.FEATURE) f = rf.get(n) f.set_representation([n1.get_id(), n2.get_id()]) childf = rf.get(n.add_child("child feat", RMF.FEATURE)) childf.set_representation([n1.get_id(), n2.get_id()]) f = rf.get(rn.add_child("feat 2", RMF.FEATURE)) f.set_representation([n2.get_id(), n3.get_id()]) # 3-particle feature (should be ignored) f = rf.get(rn.add_child("feat 3", RMF.FEATURE)) f.set_representation([n1.get_id(), n2.get_id(), n3.get_id()]) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) # Three features (and one child) should have been added features = structures[0].rmf_features self.assertEqual(len(features), 3) self.assertIsInstance(features[0].chimera_obj, Pseudobond) self.assertIsInstance(features[1].chimera_obj, Pseudobond) self.assertIsInstance(features[2].chimera_obj, Atoms) child_feat, = features[0].children self.assertIsInstance(child_feat.chimera_obj, Pseudobond)
def clang_frontend(args): """Generate Boogie code from C-language source(s).""" bitcodes = [] compile_command = default_clang_compile_command(args) for c in args.input_files: bc = temporary_file(os.path.splitext(os.path.basename(c))[0], '.bc', args) try_command(compile_command + ['-o', bc, c], console=True) bitcodes.append(bc) try_command(['llvm-link', '-o', args.bc_file] + bitcodes) try_command(['llvm-link', '-o', args.linked_bc_file, args.bc_file] + build_libs(args)) llvm_to_bpl(args)
def clang_frontend(args): """Generate Boogie code from C-language source(s).""" bitcodes = [] compile_command = default_clang_compile_command(args) for c in args.input_files: bc = temporary_file(os.path.splitext(os.path.basename(c))[0], '.bc', args) try_command(compile_command + ['-o', bc, c], console=True) bitcodes.append(bc) try_command(['llvm-link', '-o', args.bc_file] + bitcodes) try_command(['llvm-link', '-o', args.linked_bc_file, args.bc_file] + build_libs(args)) llvm_to_bpl(args)
def build_libs(args): """Generate LLVM bitcodes for SMACK libraries.""" bitcodes = [] libs = ['smack.c'] if args.pthread: libs += ['pthread.c'] for c in map(lambda c: os.path.join(smack_lib(), c), libs): bc = temporary_file(os.path.splitext(os.path.basename(c))[0], '.bc', args) try_command(default_clang_compile_command(args, True) + ['-o', bc, c]) bitcodes.append(bc) return bitcodes
def test_em2d_provenance(self): """Test open_rmf handling of RMF EM2D restraint provenance""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) imp_restraint_cat = r.get_category("IMP restraint") rsr_typek = r.get_key(imp_restraint_cat, "type", RMF.StringTag()) rsr_pixelsizek = r.get_key(imp_restraint_cat, "pixel size", RMF.FloatTag()) imp_restraint_fn_cat = r.get_category("IMP restraint files") rsr_imagefilesk = r.get_key(imp_restraint_fn_cat, "image files", RMF.StringsTag()) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() represf = RMF.RepresentationFactory(r) particlef = RMF.ParticleFactory(r) pn = rn.add_child("p1", RMF.REPRESENTATION) p = particlef.get(pn) p.set_mass(12.) p.set_radius(1.) p.set_coordinates(RMF.Vector3(1, 2, 3)) n = rn.add_child("nofname", RMF.FEATURE) p = represf.get(n) p.set_representation([pn]) n.set_value(rsr_typek, "IMP.em2d.PCAFitRestraint") n = rn.add_child("emr", RMF.FEATURE) p = represf.get(n) p.set_representation([pn]) n.set_value(rsr_typek, "IMP.em2d.PCAFitRestraint") n.set_value(rsr_pixelsizek, 1.0) n.set_value(rsr_imagefilesk, ["abc", "def"]) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) p1, p2 = structures[0].rmf_provenance self.assertIsInstance(p1, src.io._RMFEM2DRestraintProvenance) self.assertEqual(p1.name, 'EM class average from abc') self.assertAlmostEqual(p1.pixel_size, 1.0, delta=1e-6) self.assertIsInstance(p2, src.io._RMFEM2DRestraintProvenance) self.assertEqual(p2.name, 'EM class average from def') self.assertAlmostEqual(p2.pixel_size, 1.0, delta=1e-6)
def target_selection(args): """Determine the target architecture based on flags and source files.""" # TODO more possible clang flags that determine the target? if not re.search('-target', args.clang_options): src = args.input_files[0] if os.path.splitext(src)[1] == '.bc': ll = temporary_file(os.path.splitext(os.path.basename(src))[0], '.ll', args) try_command(['llvm-dis', '-o', ll, src]) src = ll if os.path.splitext(src)[1] == '.ll': with open(src, 'r') as f: for line in f: triple = re.findall('^target triple = "(.*)"', line) if len(triple) > 0: args.clang_options += (" -target %s" % triple[0]) break
def target_selection(args): """Determine the target architecture based on flags and source files.""" # TODO more possible clang flags that determine the target? if not re.search('-target', args.clang_options): src = args.input_files[0] if os.path.splitext(src)[1] == '.bc': ll = temporary_file(os.path.splitext(os.path.basename(src))[0], '.ll', args) try_command(['llvm-dis', '-o', ll, src]) src = ll if os.path.splitext(src)[1] == '.ll': with open(src, 'r') as f: for line in f: triple = re.findall('^target triple = "(.*)"', line) if len(triple) > 0: args.clang_options += (" -target %s" % triple[0]) break
def test_alternatives(self): """Test open_rmf handling of RMF alternatives""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() af = RMF.AlternativesFactory(r) pf = RMF.ParticleFactory(r) gf = RMF.GaussianParticleFactory(r) n = rn.add_child("topp1", RMF.REPRESENTATION) p = n.add_child("p1", RMF.REPRESENTATION) b = pf.get(p) b.set_mass(1) b.set_radius(4) b.set_coordinates(RMF.Vector3(4., 5., 6.)) a = af.get(n) root = r.add_node("topp2", RMF.REPRESENTATION) p = root.add_child("p2", RMF.REPRESENTATION) b = pf.get(p) b.set_radius(4) b.set_coordinates(RMF.Vector3(4., 5., 6.)) a.add_alternative(root, RMF.PARTICLE) root = r.add_node("topg1", RMF.REPRESENTATION) g = root.add_child("g1", RMF.REPRESENTATION) b = gf.get(g) b.set_variances(RMF.Vector3(1., 1., 1.)) b.set_mass(1.) b = pf.get(g) b.set_radius(4) b.set_coordinates(RMF.Vector3(4., 5., 6.)) a.add_alternative(root, RMF.GAUSSIAN_PARTICLE) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) root = structures[0].rmf_hierarchy self.assertEqual(root.name, 'root') # All alternatives should be children of the root self.assertEqual([c.name for c in root.children], ['topp1', 'topp2', 'topg1'])
def test_em_provenance(self): """Test open_rmf handling of RMF EM restraint provenance""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) imp_restraint_cat = r.get_category("IMP restraint") rsr_typek = r.get_key(imp_restraint_cat, "type", RMF.StringTag()) imp_restraint_fn_cat = r.get_category("IMP restraint files") rsr_filenamek = r.get_key(imp_restraint_fn_cat, "filename", RMF.StringTag()) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() represf = RMF.RepresentationFactory(r) particlef = RMF.ParticleFactory(r) pn = rn.add_child("p1", RMF.REPRESENTATION) p = particlef.get(pn) p.set_mass(12.) p.set_radius(1.) p.set_coordinates(RMF.Vector3(1, 2, 3)) n = rn.add_child("r1", RMF.FEATURE) p = represf.get(n) p.set_representation([pn]) n.set_value(rsr_typek, "some other restraint") n = rn.add_child("nofname", RMF.FEATURE) p = represf.get(n) p.set_representation([pn]) n.set_value(rsr_typek, "IMP.isd.GaussianEMRestraint") n = rn.add_child("emr", RMF.FEATURE) p = represf.get(n) p.set_representation([pn]) n.set_value(rsr_typek, "IMP.isd.GaussianEMRestraint") n.set_value(rsr_filenamek, "abc") with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) p1, = structures[0].rmf_provenance self.assertIsInstance(p1, src.io._RMFEMRestraintGMMProvenance)
def test_command_0(tmpdir): for row in range(5): file_ = temporary_file(tmpdir, CONTENT[row]) found = command0(file_) for key, value in found.items(): print(key, value) if row == 2: assert "ellis-101" in found[0] if row == 3: assert "ell-a01" in found[0] if row == 4: assert "ell-0010" in found[0] if row == 0: assert "ell-001" in found['transcriber_id'] if row == 1: assert "bul-011" in found['transcriber_id']
def test_command_7(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command7(file_) keys = sorted(found.keys()) for key in keys: print(key, found[key]) assert 1 not in found assert 2 not in found assert 3 not in found assert 4 in found assert 5 not in found assert 6 in found assert 7 in found assert 8 in found assert 9 in found assert 10 not in found assert 11 not in found assert 12 in found assert 13 not in found assert 14 in found assert 15 in found assert 16 in found assert 17 in found assert 18 in found assert 19 in found assert 20 in found assert 21 not in found assert 22 in found assert 23 in found assert 24 not in found assert 25 not in found assert 26 not in found assert 27 not in found assert 28 not in found assert 29 not in found assert 30 in found assert 31 in found assert 32 not in found assert 33 not in found assert 34 in found assert 35 in found assert 36 not in found
def build_libs(args): """Generate LLVM bitcodes for SMACK libraries.""" bitcodes = [] libs = ['smack.c'] if args.pthread: libs += ['pthread.c'] if args.memory_safety or args.signed_integer_overflow: libs += ['string.c'] if args.float: libs += ['math.c'] for c in map(lambda c: os.path.join(smack_lib(), c), libs): bc = temporary_file(os.path.splitext(os.path.basename(c))[0], '.bc', args) try_command(default_clang_compile_command(args, True) + ['-o', bc, c]) bitcodes.append(bc) return bitcodes
def test_read_atoms_het(self): """Test open_rmf handling of RMF atoms with HET prefix""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() atomf = RMF.AtomFactory(r) particlef = RMF.ParticleFactory(r) chainf = RMF.ChainFactory(r) residuef = RMF.ResidueFactory(r) n = rn.add_child("H", RMF.REPRESENTATION) c = chainf.get(n) c.set_chain_id('H') def add_residue(n, atom_name, resnum, res_name): n = n.add_child("%d" % resnum, RMF.REPRESENTATION) r = residuef.get(n) r.set_residue_index(resnum) r.set_residue_type(res_name) n = n.add_child(atom_name, RMF.REPRESENTATION) a = atomf.get(n) a.set_element(12) p = particlef.get(n) p.set_mass(12.) p.set_radius(1.) p.set_coordinates(RMF.Vector3(1, 2, 3)) add_residue(n, 'HET: N ', 1, 'PCA') add_residue(n, 'C', 2, 'GLY') with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) # Two atoms in two residues should have been added state, = structures[0].child_models() self.assertEqual(len(state.residues), 2) self.assertEqual(len(state.atoms), 2) a1, a2 = state.atoms self.assertEqual(a1.name, 'N') self.assertEqual(a2.name, 'C')
def replay_error_trace(verifier_output, args): if args.verifier != 'corral': print "Replay for verifiers other than 'corral' currently unsupported; skipping replay" return print "Attempting to replay error trace." missing_definitions = detect_missing_definitions(args.bc_file) if '__SMACK_code' in missing_definitions: print "warning: inline Boogie code found; replay may fail" arguments, return_values = extract_values(verifier_output) with open(args.replay_harness, 'w') as f: f.write(harness(arguments, return_values, missing_definitions)) print "Generated replay harness:", args.replay_harness stubs_bc = temporary_file('stubs', '.bc', args) try_command( ['clang', '-c', '-emit-llvm', '-o', stubs_bc, args.replay_harness]) try_command([ 'clang', '-Wl,-e,_smack_replay_main', '-o', args.replay_exe_file, args.bc_file, stubs_bc ]) print "Generated replay executable:", args.replay_exe_file try: if 'error reached!' in try_command(["./" + args.replay_exe_file]): print "Error-trace replay successful." return True else: print "Error-trace replay failed." except Exception as err: print "Error-trace replay caught", err.message return False
def test_rmf_em_restraint_provenance(self): """Test _RMFEMRestraintProvenance class""" rmf_node = MockRMFNode("r1", 1) # Test with non-existent GMM file p = src.io._RMFEMRestraintGMMProvenance(rmf_node, '/does/notexist') self.assertEqual(p.name, 'Gaussian Mixture Model from notexist') self.assertIsNone(p.previous) p.load(None, None) # noop # Test with GMM file containing no metadata with utils.temporary_file(suffix='.gmm') as fname: with open(fname, 'w') as fh: pass p = src.io._RMFEMRestraintGMMProvenance(rmf_node, fname) self.assertIsNone(p.previous) # Test with GMM file containing valid metadata with utils.temporary_directory() as tmpdir: gmm = os.path.join(tmpdir, 'test.gmm') mrc = os.path.join(tmpdir, 'test.mrc2') with open(gmm, 'w') as fh: fh.write("""# Created by create_gmm.py # data_fn: test.mrc2 # ncenters: 50 """) with open(mrc, 'w') as fh: pass p = src.io._RMFEMRestraintGMMProvenance(rmf_node, gmm) prev = p.previous self.assertEqual(prev.filename, mrc) self.assertEqual(p.name, 'Gaussian Mixture Model from test.gmm') self.assertEqual(prev.name, 'EM map from test.mrc2') mock_session = make_session() mock_session.logger = MockLogger() model = src.io._RMFModel(mock_session, 'fname') # Should be a noop since mrc2 isn't a known map format prev.load(mock_session, model)
def fortran_compile_to_bc(input_file, compile_command, args): """Compile a FORTRAN source file to LLVM IR.""" # This method only exists as a hack to get flang to work # with SMACK. When we update to the latest flang on LLVM 5, # this method will no longer be necessary. The hack is # self-contained in this method. # The Debug Info Version in flang is incompatible with # the version that clang uses. The workaround is to use # sed to change the file so llvm-link gives a warning # and not an error. # compile to human-readable format in order to tweak the IR compile_command[1] = '-S' ll = temporary_file(os.path.splitext(os.path.basename(input_file))[0], '.ll', args) try_command(compile_command + ['-o', ll, input_file], console=True) # change the throw level of 'Debug Info Version' from error to warning in the IR try_command(['sed', '-i', 's/i32 1, !\"Debug Info Version\"/i32 2, !\"Debug Info Version\"/g', ll]) try_command(['llvm-as', ll]) try_command(['rm', ll]) bc = '.'.join(ll.split('.')[:-1] + ['bc']) return bc
def test_read_balls(self): """Test readtraj handling of RMF Balls""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() bf = RMF.BallFactory(r) cf = RMF.ColoredFactory(r) n = rn.add_child("ball", RMF.GEOMETRY) b1 = bf.get(n) b1.set_radius(6) b1.set_coordinates(RMF.Vector3(1., 2., 3.)) c1 = cf.get(n) c1.set_rgb_color(RMF.Vector3(1, 0, 0)) b2 = bf.get(rn.add_child("ball", RMF.GEOMETRY)) b2.set_radius(4) b2.set_coordinates(RMF.Vector3(4., 5., 6.)) # no color r.add_frame("f1", RMF.FRAME) r.add_frame("f2", RMF.FRAME) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() mock_session.logger = MockLogger() structures, status = src.io.open_rmf(mock_session, fname) state = structures[0].child_models()[0] # Just one frame to start with self.assertEqual(list(state.coordset_ids), [1]) # Test noop read of structure src.cmd.readtraj(mock_session, structures[0]) src.cmd.readtraj(mock_session, state, last=1) # Two frames should have been read self.assertEqual(list(state.coordset_ids), [1, 2])
def test_read_balls(self): """Test open_rmf handling of RMF Balls""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() bf = RMF.BallFactory(r) cf = RMF.ColoredFactory(r) n = rn.add_child("ball", RMF.GEOMETRY) b1 = bf.get(n) b1.set_radius(6) b1.set_coordinates(RMF.Vector3(1., 2., 3.)) c1 = cf.get(n) c1.set_rgb_color(RMF.Vector3(1, 0, 0)) b2 = bf.get(rn.add_child("ball", RMF.GEOMETRY)) b2.set_radius(4) b2.set_coordinates(RMF.Vector3(4., 5., 6.)) # no color with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() structures, status = src.io.open_rmf(mock_session, fname) # Two atoms (in a single residue in the unnamed state) # should have been added state, = structures[0].child_models() self.assertEqual(len(state.residues), 1) self.assertEqual(len(state.atoms), 2) a1, a2 = state.atoms # Default element self.assertEqual(a1.element.name, 'C') self.assertEqual(a2.element.name, 'C') self.assertEqual([int(c) for c in a1.coord], [1, 2, 3]) self.assertEqual([int(c) for c in a2.coord], [4, 5, 6])
def test_nest_refframe(self): """Test readtraj handling of nested reference frames""" def make_rmf_file(fname): r = RMF.create_rmf_file(fname) r.add_frame("root", RMF.FRAME) rn = r.get_root_node() bf = RMF.BallFactory(r) rff = RMF.ReferenceFrameFactory(r) n = rn.add_child("toprf", RMF.REPRESENTATION) rf = rff.get(n) rf.set_rotation(RMF.Vector4(1, 0, 0, 0)) rf.set_translation(RMF.Vector3(1, 2, 3)) n = n.add_child("botrf", RMF.REPRESENTATION) rf = rff.get(n) rf.set_rotation(RMF.Vector4(1, 0, 0, 0)) rf.set_translation(RMF.Vector3(9, 8, 7)) n = n.add_child("ball", RMF.GEOMETRY) b1 = bf.get(n) b1.set_radius(6) b1.set_coordinates(RMF.Vector3(4., 5., 6.)) r.add_frame("f1", RMF.FRAME) r.add_frame("f2", RMF.FRAME) with utils.temporary_file(suffix='.rmf') as fname: make_rmf_file(fname) mock_session = make_session() mock_session.logger = MockLogger() structures, status = src.io.open_rmf(mock_session, fname) state = structures[0].child_models()[0] # One atom should have been read, and transformed twice atom, = state.atoms # Truncate so comparison is exact self.assertEqual([int(x) for x in atom.coord], [14, 15, 16]) src.cmd.readtraj(mock_session, state)
def d_compile_to_bc(input_file, compile_command, args): """Compile a D source file to LLVM IR.""" bc = temporary_file( os.path.splitext(os.path.basename(input_file))[0], '.bc', args) try_command(compile_command + ['-of=' + bc, input_file], console=True) return bc
def arguments(): """Parse command-line arguments""" parser = argparse.ArgumentParser() parser.add_argument('input_files', metavar='input-files', nargs='+', action=FileAction, type = str, help = 'source file to be translated/verified') parser.add_argument('--version', action='version', version='SMACK version ' + VERSION) noise_group = parser.add_mutually_exclusive_group() noise_group.add_argument('-q', '--quiet', action='store_true', default=False, help='enable quiet output') noise_group.add_argument('-v', '--verbose', action='store_true', default=False, help='enable verbose output') noise_group.add_argument('-d', '--debug', action="store_true", default=False, help='enable debugging output') noise_group.add_argument('--debug-only', metavar='MODULES', default=None, type=str, help='limit debugging output to given MODULES') parser.add_argument('-t', '--no-verify', action="store_true", default=False, help='perform only translation, without verification.') parser.add_argument('-w', '--error-file', metavar='FILE', default=None, type=str, help='save error trace/witness to FILE') frontend_group = parser.add_argument_group('front-end options') frontend_group.add_argument('-x', '--language', metavar='LANG', choices=frontends().keys(), default=None, help='Treat input files as having type LANG.') frontend_group.add_argument('-bc', '--bc-file', metavar='FILE', default=None, action=FileAction, type=str, help='save initial LLVM bitcode to FILE') frontend_group.add_argument('--linked-bc-file', metavar='FILE', default=None, type=str, help=argparse.SUPPRESS) frontend_group.add_argument('--replay-harness', metavar='FILE', default='replay-harness.c', type=str, help=argparse.SUPPRESS) frontend_group.add_argument('--replay-exe-file', metavar='FILE', default='replay-exe', type=str, help=argparse.SUPPRESS) frontend_group.add_argument('-ll', '--ll-file', metavar='FILE', default=None, action=FileAction, type=str, help='save final LLVM IR to FILE') frontend_group.add_argument('--clang-options', metavar='OPTIONS', default='', help='additional compiler arguments (e.g., --clang-options="-w -g")') translate_group = parser.add_argument_group('translation options') translate_group.add_argument('-bpl', '--bpl-file', metavar='FILE', default=None, action=FileAction, type=str, help='save (intermediate) Boogie code to FILE') translate_group.add_argument('--no-memory-splitting', action="store_true", default=False, help='disable region-based memory splitting') translate_group.add_argument('--mem-mod', choices=['no-reuse', 'no-reuse-impls', 'reuse'], default='no-reuse-impls', help='select memory model (no-reuse=never reallocate the same address, reuse=reallocate freed addresses) [default: %(default)s]') translate_group.add_argument('--static-unroll', action="store_true", default=False, help='enable static LLVM loop unrolling pass as a preprocessing step') translate_group.add_argument('--pthread', action='store_true', default=False, help='enable support for pthread programs') translate_group.add_argument('--bit-precise', action="store_true", default=False, help='enable bit precision for non-pointer values') translate_group.add_argument('--timing-annotations', action="store_true", default=False, help='enable timing annotations') translate_group.add_argument('--bit-precise-pointers', action="store_true", default=False, help='enable bit precision for pointer values') translate_group.add_argument('--no-byte-access-inference', action="store_true", default=False, help='disable bit-precision-related optimizations with DSA') translate_group.add_argument('--entry-points', metavar='PROC', nargs='+', default=['main'], help='specify top-level procedures [default: %(default)s]') translate_group.add_argument('--memory-safety', action='store_true', default=False, help='enable memory safety checks') translate_group.add_argument('--only-check-valid-deref', action='store_true', default=False, help='only enable valid dereference checks') translate_group.add_argument('--only-check-valid-free', action='store_true', default=False, help='only enable valid free checks') translate_group.add_argument('--only-check-memleak', action='store_true', default=False, help='only enable memory leak checks') translate_group.add_argument('--integer-overflow', action='store_true', default=False, help='enable integer overflow checks') translate_group.add_argument('--float', action="store_true", default=False, help='enable bit-precise floating-point functions') translate_group.add_argument('--strings', action='store_true', default=False, help='enable support for string') verifier_group = parser.add_argument_group('verifier options') verifier_group.add_argument('--verifier', choices=['boogie', 'corral', 'symbooglix', 'duality', 'svcomp'], default='corral', help='back-end verification engine') verifier_group.add_argument('--unroll', metavar='N', default='1', type = lambda x: int(x) if int(x) > 0 else parser.error('Unroll bound has to be positive.'), help='loop/recursion unroll bound [default: %(default)s]') verifier_group.add_argument('--loop-limit', metavar='N', default='1', type=int, help='upper bound on minimum loop iterations [default: %(default)s]') verifier_group.add_argument('--context-bound', metavar='K', default='1', type=int, help='bound on the number of thread contexts in Corral [default: %(default)s]') verifier_group.add_argument('--verifier-options', metavar='OPTIONS', default='', help='additional verifier arguments (e.g., --verifier-options="/trackAllVars /staticInlining")') verifier_group.add_argument('--time-limit', metavar='N', default='1200', type=int, help='verifier time limit, in seconds [default: %(default)s]') verifier_group.add_argument('--max-violations', metavar='N', default='1', type=int, help='maximum reported assertion violations [default: %(default)s]') verifier_group.add_argument('--smackd', action="store_true", default=False, help='generate JSON-format output for SMACKd') verifier_group.add_argument('--svcomp-property', metavar='FILE', default=None, type=str, help='load SVCOMP property to check from FILE') verifier_group.add_argument('--modular', action="store_true", default=False, help='enable contracts-based modular deductive verification (uses Boogie)') verifier_group.add_argument('--replay', action="store_true", default=False, help='enable reply of error trace with test harness.') plugins_group = parser.add_argument_group('plugins') plugins_group.add_argument('--transform-bpl', metavar='COMMAND', default=None, type=str, help='transform generated Boogie code via COMMAND') plugins_group.add_argument('--transform-out', metavar='COMMAND', default=None, type=str, help='transform verifier output via COMMAND') args = parser.parse_args() if not args.bc_file: args.bc_file = temporary_file('a', '.bc', args) if not args.linked_bc_file: args.linked_bc_file = temporary_file('b', '.bc', args) if not args.bpl_file: args.bpl_file = 'a.bpl' if args.no_verify else temporary_file('a', '.bpl', args) if args.only_check_valid_deref or args.only_check_valid_free or args.only_check_memleak: args.memory_safety = True # TODO are we (still) using this? # with open(args.input_file, 'r') as f: # for line in f.readlines(): # m = re.match('.*SMACK-OPTIONS:[ ]+(.*)$', line) # if m: # return args = parser.parse_args(m.group(1).split() + sys.argv[1:]) return args
def test_command25(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command25(file_) for key in sorted(found.keys()): print(key, found[key]) assert "Unexpected white space in Turn tag" in found[1] assert 'Tag syntax error' in found[2] assert not 3 in found assert not 4 in found assert "Unexpected white space in Turn tag" in found[5] assert "Unexpected white space in Sync tag" in found[6] assert not 7 in found assert not 8 in found assert "Unexpected white space in Turn tag" in found[9] assert "Unexpected white space in Sync tag" in found[10] assert not 11 in found assert not 12 in found assert "Unexpected white space in Turn tag" in found[13] assert "Unexpected white space in Sync tag" in found[14] assert not 15 in found assert not 16 in found assert "Unexpected white space in Turn tag" in found[17] assert "Unexpected white space in Sync tag" in found[18] assert not 19 in found assert not 20 in found assert "Unexpected white space in Turn tag" in found[21] assert "Unexpected white space in Sync tag" in found[22] assert not 23 in found assert not 24 in found assert "Unexpected white space in Turn tag" in found[25] assert "Unexpected white space in Sync tag" in found[26] assert not 27 in found assert not 28 in found assert not 29 in found assert not 30 in found assert not 31 in found assert not 32 in found assert "Unexpected white space in Turn tag" in found[33] assert "Tag syntax error" in found[34] assert not 35 in found assert not 36 in found assert "Unexpected white space in Turn tag" in found[37] assert 38 not in found assert not 39 in found assert not 40 in found assert "Unexpected white space in Turn tag" in found[41] assert "Unexpected white space in Turn tag" in found[42] assert "Unexpected white space in Turn tag" in found[43] assert "Unexpected white space in Turn tag" in found[44] assert "Unexpected white space in Turn tag" in found[45] assert "Unexpected white space in Turn tag" in found[46] assert "Tag syntax error" in found[47] assert "Tag syntax error" in found[48] #assert 49 in found assert "Tag syntax error" in found[50] #assert 51 in found assert 52 not in found assert 53 not in found assert "Tag syntax error" in found[54] assert 55 not in found assert 56 not in found assert "Empty row in Sync tag" in found[59] assert "Empty row in Sync tag" in found[65] assert 57 not in found assert 58 not in found assert 60 not in found assert 61 not in found assert 62 not in found assert 63 not in found assert 64 not in found assert 66 not in found assert 67 not in found assert 68 not in found assert 69 not in found assert 70 not in found assert 71 not in found assert 72 not in found
def d_compile_to_bc(input_file, compile_command, args): """Compile a D source file to LLVM IR.""" bc = temporary_file(os.path.splitext(os.path.basename(input_file))[0], '.bc', args) try_command(compile_command + ['-of=' + bc, input_file], console=True) return bc
def test_command_22(tmpdir): file_ = temporary_file(tmpdir, CONTENT) found = command22(file_) for key in sorted(found.keys()): print(key, found[key])
def arguments(): """Parse command-line arguments""" parser = argparse.ArgumentParser() parser.add_argument('input_files', metavar='input-files', nargs='+', action=FileAction, type=str, help='source file to be translated/verified') parser.add_argument('--version', action='version', version='SMACK version ' + VERSION) noise_group = parser.add_mutually_exclusive_group() noise_group.add_argument('-q', '--quiet', action='store_true', default=False, help='enable quiet output') noise_group.add_argument('-v', '--verbose', action='store_true', default=False, help='enable verbose output') noise_group.add_argument('-d', '--debug', action="store_true", default=False, help='enable debugging output') noise_group.add_argument('--debug-only', metavar='MODULES', default=None, type=str, help='limit debugging output to given MODULES') noise_group.add_argument('--warn', default="unsound", choices=['silent', 'unsound', 'info'], help='''enable certain type of warning messages (silent: no warning messages; unsound: warnings about unsoundness; info: warnings about unsoundness and translation information) [default: %(default)s]''' ) parser.add_argument('-t', '--no-verify', action="store_true", default=False, help='perform only translation, without verification.') parser.add_argument('-w', '--error-file', metavar='FILE', default=None, type=str, help='save error trace/witness to FILE') frontend_group = parser.add_argument_group('front-end options') frontend_group.add_argument('-x', '--language', metavar='LANG', choices=frontends().keys(), default=None, help='Treat input files as having type LANG.') frontend_group.add_argument('-bc', '--bc-file', metavar='FILE', default=None, action=FileAction, type=str, help='save initial LLVM bitcode to FILE') frontend_group.add_argument('--linked-bc-file', metavar='FILE', default=None, type=str, help=argparse.SUPPRESS) frontend_group.add_argument('--replay-harness', metavar='FILE', default='replay-harness.c', type=str, help=argparse.SUPPRESS) frontend_group.add_argument('--replay-exe-file', metavar='FILE', default='replay-exe', type=str, help=argparse.SUPPRESS) frontend_group.add_argument('-ll', '--ll-file', metavar='FILE', default=None, action=FileAction, type=str, help='save final LLVM IR to FILE') frontend_group.add_argument( '--clang-options', metavar='OPTIONS', default='', help='additional compiler arguments (e.g., --clang-options="-w -g")') translate_group = parser.add_argument_group('translation options') translate_group.add_argument( '-bpl', '--bpl-file', metavar='FILE', default=None, action=FileAction, type=str, help='save (intermediate) Boogie code to FILE') translate_group.add_argument('--no-memory-splitting', action="store_true", default=False, help='disable region-based memory splitting') translate_group.add_argument( '--mem-mod', choices=['no-reuse', 'no-reuse-impls', 'reuse'], default='no-reuse-impls', help= 'select memory model (no-reuse=never reallocate the same address, reuse=reallocate freed addresses) [default: %(default)s]' ) translate_group.add_argument( '--static-unroll', action="store_true", default=False, help='enable static LLVM loop unrolling pass as a preprocessing step') translate_group.add_argument('--pthread', action='store_true', default=False, help='enable support for pthread programs') translate_group.add_argument( '--bit-precise', action="store_true", default=False, help='model non-pointer values as bit vectors') translate_group.add_argument('--timing-annotations', action="store_true", default=False, help='enable timing annotations') translate_group.add_argument( '--bit-precise-pointers', action="store_true", default=False, help='model pointers and non-pointer values as bit vectors') translate_group.add_argument( '--no-byte-access-inference', action="store_true", default=False, help='disable bit-precision-related optimizations with DSA') translate_group.add_argument( '--entry-points', metavar='PROC', nargs='+', default=['main'], help='specify top-level procedures [default: %(default)s]') translate_group.add_argument('--memory-safety', action='store_true', default=False, help='enable memory safety checks') translate_group.add_argument('--only-check-valid-deref', action='store_true', default=False, help='only enable valid dereference checks') translate_group.add_argument('--only-check-valid-free', action='store_true', default=False, help='only enable valid free checks') translate_group.add_argument('--only-check-memleak', action='store_true', default=False, help='only enable memory leak checks') translate_group.add_argument('--integer-overflow', action='store_true', default=False, help='enable integer overflow checks') translate_group.add_argument( '--float', action="store_true", default=False, help='enable bit-precise floating-point functions') translate_group.add_argument('--strings', action='store_true', default=False, help='enable support for string') verifier_group = parser.add_argument_group('verifier options') verifier_group.add_argument( '--verifier', choices=['boogie', 'corral', 'symbooglix', 'svcomp'], default='corral', help='back-end verification engine') verifier_group.add_argument( '--unroll', metavar='N', default='1', type=lambda x: int(x) if int(x) > 0 else parser.error('Unroll bound has to be positive.'), help='loop/recursion unroll bound [default: %(default)s]') verifier_group.add_argument( '--loop-limit', metavar='N', default='1', type=int, help='upper bound on minimum loop iterations [default: %(default)s]') verifier_group.add_argument( '--context-bound', metavar='K', default='1', type=int, help= 'bound on the number of thread contexts in Corral [default: %(default)s]' ) verifier_group.add_argument( '--verifier-options', metavar='OPTIONS', default='', help= 'additional verifier arguments (e.g., --verifier-options="/trackAllVars /staticInlining")' ) verifier_group.add_argument( '--time-limit', metavar='N', default='1200', type=int, help='verifier time limit, in seconds [default: %(default)s]') verifier_group.add_argument( '--max-violations', metavar='N', default='1', type=int, help='maximum reported assertion violations [default: %(default)s]') verifier_group.add_argument('--smackd', action="store_true", default=False, help='generate JSON-format output for SMACKd') verifier_group.add_argument('--svcomp-property', metavar='FILE', default=None, type=str, help='load SVCOMP property to check from FILE') verifier_group.add_argument( '--modular', action="store_true", default=False, help= 'enable contracts-based modular deductive verification (uses Boogie)') verifier_group.add_argument( '--replay', action="store_true", default=False, help='enable reply of error trace with test harness.') plugins_group = parser.add_argument_group('plugins') plugins_group.add_argument( '--transform-bpl', metavar='COMMAND', default=None, type=str, help='transform generated Boogie code via COMMAND') plugins_group.add_argument('--transform-out', metavar='COMMAND', default=None, type=str, help='transform verifier output via COMMAND') args = parser.parse_args() if not args.bc_file: args.bc_file = temporary_file('a', '.bc', args) if not args.linked_bc_file: args.linked_bc_file = temporary_file('b', '.bc', args) if not args.bpl_file: args.bpl_file = 'a.bpl' if args.no_verify else temporary_file( 'a', '.bpl', args) if args.only_check_valid_deref or args.only_check_valid_free or args.only_check_memleak: args.memory_safety = True if args.bit_precise_pointers: args.bit_precise = True # TODO are we (still) using this? # with open(args.input_file, 'r') as f: # for line in f.readlines(): # m = re.match('.*SMACK-OPTIONS:[ ]+(.*)$', line) # if m: # return args = parser.parse_args(m.group(1).split() + sys.argv[1:]) return args
def test_rmf_structure_provenance(self): """Test _RMFStructureProvenance class""" class MockStructureProvenance: def get_chain(self): return self.chain def get_residue_offset(self): return self.residue_offset def get_filename(self): return self.filename prov = MockStructureProvenance() prov.chain = 'A' prov.residue_offset = 0 prov.filename = '/does/notexist' rmf_node = MockRMFNode("r1", 1) provenance_chains = {} p = src.io._RMFStructureProvenance(rmf_node, prov, provenance_chains) self.assertEqual(p.name, 'Chain A from notexist') self.assertEqual(p.chain, 'A') self.assertEqual(p.allchains, set('A')) mock_session = make_session() s = p.take_snapshot(mock_session, None) newp = src.io._RMFStructureProvenance.restore_snapshot(mock_session, s) self.assertIsInstance(newp, src.io._RMFStructureProvenance) prov2 = MockStructureProvenance() prov2.chain = 'B' prov2.residue_offset = 0 prov2.filename = '/does/notexist' rmf_node2 = MockRMFNode("r2", 2) p2 = src.io._RMFStructureProvenance( rmf_node2, prov2, provenance_chains) self.assertEqual(p2.chain, 'B') self.assertEqual(p2.allchains, set('AB')) # allchains should have been updated for p too self.assertEqual(p.allchains, set('AB')) # Test with non-existent file mock_session = make_session() mock_session.logger = MockLogger() model = src.io._RMFModel(mock_session, 'fname') p.load(mock_session, model) self.assertIn('does not exist', mock_session.logger.warning_log[0][0]) # File that does exist but unrecognized file format (not PDB, mmCIF) with utils.temporary_file(suffix='.dcd') as fname: p.filename = fname mock_session = make_session() mock_session.logger = MockLogger() model = src.io._RMFModel(mock_session, 'fname') p.load(mock_session, model) self.assertIn('file format not recognized', mock_session.logger.warning_log[0][0]) # PDB file with utils.temporary_file(suffix='.pdb') as fname: with open(fname, 'w') as fh: fh.write("""EXPDTA THEORETICAL MODEL ATOM 1 N CYS 1 0.000 0.000 0.000 0.00999.99 N ATOM 2 CA CYS 1 1.453 0.000 0.000 0.00999.99 C END """) p.filename = fname mock_session = make_session() mock_session.logger = MockLogger() model = src.io._RMFModel(mock_session, 'fname') p.load(mock_session, model) provmodel, = model.child_models() self.assertEqual(provmodel.name, 'Provenance') self.assertEqual(len(provmodel.child_models()), 1) # Should be a noop to try to read it again p.load(mock_session, model) self.assertEqual(len(provmodel.child_models()), 1)