# A first-principles calculation with ABINIT¶

The following is a very basic calculation of Z2 invariants using ABINIT for a generic system. Before running this calculation, an SCF run is required to create a density input file.

Because this file will be quite large, it is recommended not to reference it in input_files (the first variable to fp.System), but instead reference to it directly in the .files file. This will avoid unnecessary copying.

The input files should be the same as for any NSCF run, except they should not contain any k-point information and must include a call to Wannier90. The Wannier90 input file should contain shell_list 1 and use exclude_bands to exclude non-occupied bands.

Note also that you will have to change the command that is used to call ABINIT to match your system.

#!/usr/bin/env python
# -*- coding: utf-8 -*-

import z2pack
import matplotlib.pyplot as plt

# Creating the System. Note that the SCF charge file does not need to be
# copied, but instead can be referenced in the .files file.
# The k-points input is appended to the .in file
# The command (mpirun ...) will have to be replaced to match your system.
SYSTEM_NAME = 'system'
system = z2pack.fp.System(
input_files=[
os.path.join('input', filename) for filename in [
SYSTEM_NAME + '_nscf.files', SYSTEM_NAME +
'_nscf.in', 'wannier90.win'
]
],
kpt_fct=z2pack.fp.kpoint.abinit,
kpt_path=SYSTEM_NAME + '_nscf.in',
command=
'mpirun -np 7 ~/software/abinit-7.10.5/src/98_main/abinit < {}_nscf.files >& log'
.format(SYSTEM_NAME),
executable='/bin/bash'
)

# Surface calculation for surfaces at kx=0 and kx=0.5
# Standard settings are used
res_0 = z2pack.surface.run(
system=system,
surface=lambda s, t: [0, s / 2, t],
save_file='res_0.msgpack'
)
res_1 = z2pack.surface.run(
system=system,
surface=lambda s, t: [0.5, s / 2, t],
save_file='res_1.msgpack'
)

# Combining the two plots
fig, ax = plt.subplots(1, 2, sharey=True, figsize=(9, 5))
z2pack.plot.wcc(res_0, axis=ax[0])
z2pack.plot.wcc(res_1, axis=ax[1])
plt.savefig('plot.pdf', bbox_inches='tight')

print(
'Z2 topological invariant at kx = 0: {0}'.format(
z2pack.invariant.z2(res_0)
)
)
print(
'Z2 topological invariant at kx = 0.5: {0}'.format(
z2pack.invariant.z2(res_1)
)
)