Build environment: Visual Studio 2019, Windows Forms Application, .net 4.7.2
I am attempting to use the QPDF .dll library to read, encrypt, and output a PDF file. See here for the DLL header file listing all exposed functions as declarations.
Notes:
QPDF_BOOL
is a typedef for 'int'
qpdf_r3_print_e
is an integer enum so I considered it to be 'int' also.
I can successfully initialize the QPDF library, read the file, and output it to a new file by calling the requisite functions, but when I add a call to the qpdf_set_r6_encryption_parameters2() function after initializing and successfully reading the file, it throws an access violation. This is probably because the parameter types are incorrect, but I have perused the QPDF code to the best of my ability to use the correct types.
Here is the DllImport in my C# code: (I followed this advice for all the DllImport lines)
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern void qpdf_set_r6_encryption_parameters2(
IntPtr qpdf,
[MarshalAs(UnmanagedType.LPStr)] string user_password,
[MarshalAs(UnmanagedType.LPStr)] string owner_password,
int allow_accessibility,
int allow_extract,
int allow_assemble,
int allow_annotate_and_form,
int allow_form_filling,
int allow_modify_other,
int print,
int encrypt_metadata
);
Here is the function call later in the C# code:
qpdf_set_r6_encryption_parameters2(qpdf,
txtPassword.Text,
txtPassword.Text,
0, 0, 0, 0, 0, 0,
0,
0
);
I'm fairly certain the parameter data types are wrong somewhere, but I'm not seeing it. Thanks for any pointers!
UPDATE: Here is the full code which I'm attempting to run, in case this is helpful. Note that the code works perfectly if I disable the Encryption line: it writes a new PDF file containing the same information as the input PDF.
namespace testqpdf
{
public partial class Form1 : Form
{
enum qpdf_r3_print_e
{
qpdf_r3p_full = 0,
qpdf_r3p_low = 1,
qpdf_r3p_none = 2
}
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern IntPtr qpdf_init();
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern void qpdf_cleanup(ref IntPtr qpdfData);
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern int qpdf_read(IntPtr qpdfdata, [MarshalAs(UnmanagedType.LPStr)] string fileName, IntPtr password);
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern void qpdf_set_object_stream_mode(IntPtr qpdf, int mode);
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern void qpdf_set_qdf_mode(IntPtr qpdf, int value);
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern int qpdf_init_write(IntPtr qpdf, [MarshalAs(UnmanagedType.LPStr)] string fileName);
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern int qpdf_write(IntPtr qpdf);
[DllImport("qpdf28.dll", CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)]
static extern void qpdf_set_r6_encryption_parameters2(
IntPtr qpdf,
[MarshalAs(UnmanagedType.LPStr)] string user_password,
[MarshalAs(UnmanagedType.LPStr)] string owner_password,
int allow_accessibility,
int allow_extract,
int allow_assemble,
int allow_annotate_and_form,
int allow_form_filling,
int allow_modify_other,
int print,
int encrypt_metadata
);
public Form1()
{
InitializeComponent();
}
private void btnGo_Click(object sender, EventArgs e)
{
IntPtr qpdf = qpdf_init();
int result = qpdf_read(qpdf, txtInput.Text, /* password */ IntPtr.Zero);
Console.WriteLine("Read PDF file " + txtInput.Text + ", result = " + result.ToString());
if (chkEncrypt.Checked)
{
qpdf_set_r6_encryption_parameters2(qpdf,
null,
null,
0, 0, 0, 0, 0, 0,
0,
0
);
}
result = qpdf_init_write(qpdf, txtOutput.Text);
Console.WriteLine("Write PDF file " + txtOutput.Text + ", result = " + result.ToString());
result = qpdf_write(qpdf);
qpdf_cleanup(ref qpdf);
}
}
}
Try this:
[DllImport("qpdf29.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
static extern IntPtr qpdf_init();
[DllImport("qpdf29.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
static extern void qpdf_cleanup(ref IntPtr qpdfData);
[DllImport("qpdf29.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
static extern int qpdf_read(IntPtr qpdfdata, [MarshalAs(UnmanagedType.LPStr)] string fileName, IntPtr password);
[DllImport("qpdf29.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
static extern void qpdf_set_qdf_mode(IntPtr qpdf, int value);
[DllImport("qpdf29.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
static extern int qpdf_init_write(IntPtr qpdf, [MarshalAs(UnmanagedType.LPStr)] string fileName);
[DllImport("qpdf29.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
static extern int qpdf_write(IntPtr qpdf);
IntPtr pdfData = qpdf_init();
qpdf_read(pdfData, @"C:\source file.pdf", IntPtr.Zero);
qpdf_init_write(pdfData, @"C:destination file.pdf");
qpdf_set_qdf_mode(pdfData, 1);
qpdf_write(pdfData);
qpdf_cleanup(ref pdfData);
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.