/**
 * @file public/pilot_nt.h
 * @author A. Brik, S. Papazov
 * @date 12 June 2016
 * @brief Public API for pilot_nt.dll.
 */
#ifndef _PILOT_NT_H_
#define _PILOT_NT_H_

#include <windows.h>

#ifdef UPOS
  #include "global.h"
  #include "public/paramsln.h"

#ifdef NO_VENDING_FUNCTIONS_IN_HEADER
  #define EXTERN_SPEC extern "C"
#else
  #define EXTERN_SPEC
#endif /*NO_VENDING_FIUNCTIONS_IN_HEADER*/


#if defined(__BORLANDC__) || defined(WINCE)
  #define DECL_SPEC __declspec(dllexport)
#else
  // export using def file for correct name mangling with borland underscores
  // borland use _ for cdecl
  // ms use _ for stdcall
  // we use _ with cdecl
  #define DECL_SPEC
#endif //defined(__BORLANDC__) || defined(WINCE)
#else
  #include "paramsln.h"
  #define DECL_SPEC __declspec(dllimport)
  #define EXTERN_SPEC
#endif /*UPOS*/

#define PILOT_NT_API         EXTERN_SPEC DECL_SPEC

#define PILOT_NT_VENDING_API EXTERN_SPEC DECL_SPEC

#ifdef __cplusplus
extern "C"{
#endif

/** @addtogroup HOW_TO
При оплате (возврате) покупки по банковской карте кассовая программа должна вызвать из библиотеки Сбербанка функцию card_authorize(), заполнив поля TType и Amount и указав нулевые значения в остальных полях. 
По окончании работы функции необходимо проанализировать ErrorCode (4-хзначный код ответа) или результат функции (4-хзначный код ответа). Если в нем содержится значение «0», авторизация считается успешно выполненной, в противном случае – отклоненной.
Кроме этого, необходимо проверить значение поля Check. Если оно не равно NULL, его необходимо отправить на печать (в нефискальном режиме) и затем удалить вызовом функции GlobalFree().
При закрытии смены кассовая программа должна вызвать из библиотеки Сбербанка функцию close_day(), заполнив поле TType = 7 и указав нулевые значения в остальных полях.
По окончании работы функции необходимо проверить значение поля Check. Если поле Check не равно NULL, его необходимо отправить на печать (в нефискальном режиме) и после этого удалить вызовом функции GlobaFree().
*/

/** @defgroup DOCUMENT_NAME Библиотека pilot_nt.dll
*/

/** @addtogroup PURCHASE
Пример вызова
@code
//оплата на 10 руб (1000 коп).
auth_answer aa;
memset(&aa, 0, sizeof(aa));
aa.TType=OP_PURCHASE;
aa.Amount=1000;
carderr=card_authorize(NULL, &aa);
if (carderr==0){
 // Операция прошла успешно
 // Печать чека из поля aa.Check
}
//Не забываем освободить поле auth_answer::Check
if (aa.Check)
  ::GlobalFree((HGLOBAL)aa.Check);
@endcode
*/

/** @addtogroup REFUND
Пример вызова
@code
//возврат на 10 руб (1000 коп).
auth_answer aa;
memset(&aa, 0, sizeof(aa));
aa.TType=OP_RETURN;
aa.Amount=1000;
carderr=card_authorize(NULL, &aa);
if (carderr==0){
 // Операция прошла успешно
 // Печать чека из поля aa.Check
}
//Не забываем освободить поле auth_answer::Check
if (aa.Check)
  ::GlobalFree((HGLOBAL)aa.Check);
@endcode
*/

/** @addtogroup CANCEL
Пример вызова
@code
//отмена на 10 руб (1000 коп).
auth_answer aa;
memset(&aa, 0, sizeof(aa));
aa.TType=OP_RETURN;
aa.Amount=1000;
carderr=card_authorize(NULL, &aa);
if (carderr==0){
 // Операция прошла успешно
 // Печать чека из поля aa.Check
}
//Не забываем освободить поле auth_answer::Check
if (aa.Check)
  ::GlobalFree((HGLOBAL)aa.Check);
@endcode
*/

/** @addtogroup CANCEL_WITH_RRN
Пример вызова
@code
//отмена c RRN прямой операции на 10 руб (1000 коп).
auth_answer aa;
memset(&aa, 0, sizeof(aa));
aa.TType=OP_RETURN;
aa.Amount=1000;
strcpy(aa.RRN, "123456789012");
carderr=card_authorize(NULL, &aa);
if (carderr==0){
 // Операция прошла успешно
 // Печать чека из поля aa.Check
}
//Не забываем освободить поле auth_answer::Check
if (aa.Check)
  ::GlobalFree((HGLOBAL)aa.Check);
@endcode
*/

/** @addtogroup SUSPEND
  Функция SuspendTrx()
  
  Пример вызова
  @code
    DWORD amount = 1000;
    DWORD carderr = SuspendTrx(amount, NULL);
  @endcode
  Подробный пример описан в разделе @ref FEATURE_DISASTER_CANCEL
*/
/** @addtogroup COMMIT
  Функция CommitTrx()

  Пример вызова
  @code
    DWORD amount = 1000;
    DWORD carderr = CommitTrx(amount, NULL);
  @endcode
  Подробный пример описан в разделе @ref FEATURE_DISASTER_CANCEL
*/
/** @addtogroup ROLLBACK
  Функция RollbackTrx()
  
  Пример вызова
  @code
    DWORD amount = 1000;
    DWORD carderr = RollbackTrx(amount, NULL);
  @endcode
  Подробный пример описан в разделе @ref FEATURE_DISASTER_CANCEL
*/

/** @addtogroup FEATURE_DISASTER_CANCEL
Например:
@code
//оплата на 10 руб (1000 коп).
auth_answer aa;
memset(&aa, 0, sizeof(aa));
aa.TType=OP_PURCHASE;
aa.Amount=1000;
carderr=card_authorize(NULL, &aa);
if (carderr==0){
	carderr = SuspendTrx(1000, NULL);
	//если carderr!=0, считаем операцию не выполненной, 
	//CommitTrx() или RollbackTrx() не вызываем товар не отдаем, если клиент считает, 
        //что деньги списаны, предлагаем клиенту написать претензию или сами пишем в 
	//Сбербанк с просьбой отменить операцию	
	if (действия кассы по печати чека, сохранению операции и т.п. успешны){
		if (carderr==0){
			carderr=CommitTrx(1000, NULL);
			if (carder!=0){ 
				//Отменяем операцию на кассе, товар не отдаем, если клиент считает, 
				//что деньги списаны, предлагаем клиенту написать претензию или сами пишем в Сбербанк с просьбой отменить операцию 
			}
		}
		//если carderr!=0, то подтверждать не надо, т.к. suspend отработал с ошибкой.
	}else{ 
		// действия кассы по печати чека, сохранению операции и т.п. НЕ УСПЕШНЫ
		if (carderr==0){
			carderr=RollbackTrx(1000, NULL);
			if (carderr!=0){
				//пишем письмо в Сбербанк с просьбой отменить эту операцию
			}
		}else{
			//пишем письмо в Сбербанк с просьбой отменить эту операцию (см. п.2)
		}
	}
}
//Не забываем освободить поле auth_answer::Check
if (aa.Check)
	::GlobalFree((HGLOBAL)aa.Check);
@endcode
*/

/** @addtogroup FEATURE_SPASIBO Оплата покупки с использованием баллов СПАСИБО
  Пример интеграции @see Docs\Для разработчиков ПО ККМ\examples\pilot_nt.dll\cpp\spasibo\main.cpp
*/

/** @addtogroup FEATURE_WO_CARD Выполнение операций без карты
  @warning Выполнение операций возможно только на тех версиях функций card_authorize(), которые принимают RRN в качестве параметра.
  Это функции из списка ниже:
  - card_authorize5
  - card_authorize6
  - card_authorize8
  - card_complete_multi_auth8
  - card_authorize12
  - card_authorize13
  - card_authorize14  

  Для выполнения операций возврат, отмена, завершение расчета или отмена предавторизации без карты клиента при вызове функции card_authorize() должны быть указаны следующие параметры:
  -# Аргумент Track2 – должно содержать слово «QSELECT»;
  -# Поле Amount - сумма операции, если 0 – копируется из исходной операции и кассиру предлагается подтвердить или изменить сумму, если выполняемая операция это допускает. Для операции завершение расчета сумма не должна быть равна 0, для операции отмена предавторизации сумма должна быть равна 0;
  -# Поле RRN  - номер ссылки на исходную операцию.
  -# Поля Department и CurrencyCode, при их отличии от 0 , будут использоваться как дополнительный фильтр при поиске исходных операций. При их отсутствии терминал cкопирует из исходной операции код валюты и номер отдела

Например:
@code
//оплата на 1000 руб (100000 коп).
auth_answer14 aa;
char rrn[MAX_REFNUM];  //здесь сохраним номер ссылки между оплатой и возвратом

memset(&aa, 0, sizeof(aa));
memset(&rrn, 0, sizeof(rrn));

aa.TType=OP_PURCHASE;
aa.Amount=100000;
carderr=card_authorize14(NULL, &aa);

if (carderr==0){
  //сохраняем RRN
  strcpy(rrn, aa.RRN);
  //печатаем чек, отпускаем топливо
  //все оплаченное топливо не вошло в бак, клиент уехал
  //выполняем возврат без карты

  if (aa.Check)
    ::GlobalFree((HGLOBAL)aa.Check);

  memset(&aa, 0, sizeof(aa));
  aa.TType=OP_RETURN;
  aa.Amount=2000;       //возврат 20 руб
  strcpy(aa.RRN, rrn);  //исходная операция будет найдена по ее ссылочному номеру

  carderr=card_authorize14("QSELECT", &aa);
  if (carderr==0){
    //возврат успешен, оформляем его в учетной системе
  }else{
    //что-то пошло не так. Пишем письмо в Сбербанк с описанием ситуации и просьбой вернуть клиенту 20 руб
  }
}

//Не забываем освободить поле auth_answer::Check
if (aa.Check)
  ::GlobalFree((HGLOBAL)aa.Check);

@endcode
*/

/** @addtogroup FEATURE_REQUEST_ID Уникальный идентификатор операции RequestID
  Если это необходимо, то для финансовых операций следует использовать функции ::card_authorize11, ::card_authorize12, ::card_authorize13 и ::card_authorize14.
  Значение будет возвращено в поле RequestID структур auth_answer11, auth_answer12, auth_answer13, auth_answer14 соответственно.
  
  Например:
@code{.cpp}
  //оплата на 1000 руб (100000 коп).
  auth_answer14 aa;
  memset(&aa, 0, sizeof(aa));
  memset(&rrn, 0, sizeof(rrn));

  aa.TType=OP_PURCHASE;
  aa.Amount=100000;
  carderr=card_authorize14(NULL, &aa);

  if (carderr==0){
    //поле aa.RequestID содержит уникальный идентификатор
  }

  //Не забываем освободить поле auth_answer::Check
  if (aa.Check)
    ::GlobalFree((HGLOBAL)aa.Check);
@endcode
*/

/** @addtogroup FEATURE_STATUS_REQUEST Запрос статуса операции
  Пример запроса статуса операции и чека операции:
@code{.cpp}
  auth_answer14 argument;
  // выполнение операции оплаты с заполнением структуры argument.
  // ...
  // ниже получение статуса операции с чеком
  StatusRequestQuery query;
  query.size = sizeof(StatusRequestQuery);
  query.RequestId = argument.RequestID;
  StatusRequestResult result;
  result.size = sizeof(StatusRequestResult);
  result.Cheque = NULL;
  error = GetOperationStatusByRequestId(&query, &result);
  //error - содержит код выполнения операции
  if (result.Cheque) // чек исходной операции
    ::GlobalFree((HGLOBAL)result.Cheque);
@endcode

  Пример запроса статуса операции и чека операции:
@code{.cpp}
  auth_answer14 argument;
  // выполнение операции оплаты с заполнением структуры argument.
  // ...
  // ниже получение статуса операции без получения чека
  // чек мог быть получен при исходной операции
  StatusRequestQuery query;
  query.size = sizeof(StatusRequestQuery);
  query.RequestId = argument.RequestID;
  error = GetOperationStatusByRequestId(&query, NULL);
  //error - содержит код выполнения операции
@endcode
*/

/** @addtogroup FEATURE_SEND_CHEQUE_TO_BANK
  Пример оплаты и отправки чека в терминал:
@code{.cpp}
  //оплата на 1000 руб (100000 коп).
  auth_answer14 a;
  char merchantCheque[MERH_CHEQUE_SIZE];
  
  memset(&aa, 0, sizeof(a));
  //... выполнение финансовой операции
  aa.TType=OP_PURCHASE;
  aa.Amount=100000;
  carderr=card_authorize14(NULL, &aa);

  if (carderr==0){
    //заполнение торгового чека merchantCheque[]
    //...
    //отправка чека в терминал
    ::AddMerchantCheque(aa.RequestID, merchantCheque);
    //отправка накопленых чеков к банк
    ::AddMerchantCheque(0, 0);
}

  //Не забываем освободить поле auth_answer::Check
  if (aa.Check)
    ::GlobalFree((HGLOBAL)aa.Check);
@endcode

  Пример отправки собранных чеков в банк.
     @code{.cpp}
       AddMerchantCheque(0, 0);
     @endcode

  Например: @see Docs\Для разработчиков ПО ККМ\\examples\\pilot_nt.dll\\cpp\\merh-cheque-to-host
*/

/** @addtogroup FEATURE_READ_LOYALTY_CARD
  Если требуется прочитать карту лояльности или лояльность с банковской карты без выполнения оплаты, нужно использовать функцию 
  ::ReadCardContext. Перед чтением карты необходимо создать контекст функцией ::ctxAlloc. Если предполагается чтение GooglePay Smarttap или требуется
  ограничить срабатывание функции только на магнитные карты, необходимо установить значение параметра PAR_CARD_TYPE функцией ::ctxSetInt. Можно установить следующие значения:
  -# CT_MS_ONLY     - терминал ожидает только карты с магнитной полосой. Чиповые и бесконтактные карты игнорируются, сообщение об ошибке предъявления этих карт не отображаются.
  -# CT_VAS_AND_PAY - терминал ожидает все карты и дополнительно считывает GooglePay Smarttap
  -# CT_VAS_ONLY    - терминал ожидает все карты по контактному и магнитному интерфейсу, а по бесконтакту считывает только GooglePay Smarttap. При предъявлении бесконтактной карты без GooglePay Smarttap, терминал отображает сообщение об ошибке и продолжает ждать карту.
  -# CT_VAS_AND_MS  - терминал ожидает только карты с магнитной полосой, а по бесконтакту считывает только AndroidPay Smarttap

  Параметр PAR_CARD_TYPE управляет только интерфейсами. Например, установка значения CT_MS_ONLY означает что будут считываться карты с магнитной полосой как банковские, так и карты лояльноcти.
  Окончательное отделение одних от других должно выпоняться в ККМ.
  После установки требуемых значений необходимо вызвать ::ReadCardContext, передав контекст операции в качестве параметра, дождаться завершения работы и проанализировать возвращенный результат.
  Ненулевое значение означает ошибку. Если функция завершилась без ошибок, ККМ должна считать из контекста операции требуемые данные. 
  для запроса данных используются функции ::ctxGetInt, ::ctxGetString или ctxGetBinary.
  -# PAR_LLT_ID - номер настроенной в терминале программы лояльности, которой соответсвует предъявленная карта. Запрашивается функцией ::ctxGetInt;
  -# PAR_PAN - маскированный PAN, если была предъявлена банковская карта или немаскированный PAN карты лояльности, или track2 карты лояльности, если из него не удалось выделить PAN. Запрашивается функцией ::ctxGetString;
  -# PAR_HASH - Хэш от номера карты. Если PAR_PAN содержит track2 карты лояльности, параметр не возвращается. Запрашивается функцией ::ctxGetString;
  -# PAR_CARD_TYPE - Тип считанной банковской карты. Запрашивается функцией ::ctxGetInt;
  -# PAR_OWN_CARD  - 1 - Банковская карта выпущена Сбербанком, 0 - карта выпущена сторонним банком или карта лояльности. Запрашивается функцией ::ctxGetInt;
  -# PAR_VAS_LENGTH - длина данных кошелька AndroidPay Smarttap. Запрашивается функцией ::ctxGetInt;
  -# PAR_VAS_STRING - данныt кошелька AndroidPay Smarttap. Запрашивается функцией ::ctxGetString;
  -# PAR_LLT_DATA   - номер лояльности считанный с бановской карты или карты лояльности. Запрашивается функцией ::ctxGetString.

  Если один из параметров не найден в контексте, функции ctxGet... вернут ошибку ::ERR_CTX_GET. 


  После завершения чтения карты необходимо освободить контекст операции функцией ::ctxFree.  

  Например:
@code{.cpp}
   CONTEXT_PTR ctx=ctxAlloc();

   //set card type 
   ctxSetInt(ctx, PAR_CARD_TYPE, CT_VAS_AND_MS);

   int error = ReadCardContext(ctx);

   std::cout << "ReadCardContext result=" << error << std::endl;

   if (error==ERR_OK)
   {
     std::cout << "Retrive context vars..." << std::endl;
     int ivalue;
     char buf[128];

     error = ctxGetInt(ctx, PAR_LLT_ID, &ivalue);
     if (error==ERR_OK)
     {
       std::cout << "Loyalty Id = " << ivalue << std::endl;
       error = ctxGetString(ctx, PAR_LLT_DATA, buf, sizeof(buf));
       if (error==ERR_OK)
       {
         std::cout << "Loyalty data = " << buf << std::endl;
       }
     }
     else
     {
       std::cout << "Loyalty Id is not found in context" << std::endl;
     }

     error = ctxGetString(ctx, PAR_PAN, buf, sizeof(buf));
     if (error==ERR_OK)
     {
       std::cout << "PAN = " << buf << std::endl;
     }
     else
     {
       std::cout << "PAN is not found in context" << std::endl;
     }

     error = ctxGetString(ctx, PAR_HASH, buf, sizeof(buf));
     if (error==ERR_OK)
     {
       std::cout << "HASH = " << buf << std::endl;
       hashFromReadCard=buf;
     }
     else
     {
       std::cout << "HASH is not found in context" << std::endl;
     }

     error = ctxGetInt(ctx, PAR_CARD_TYPE, &ivalue);
     if (error==ERR_OK)
     {
       std::cout << "Card type = " << ivalue << std::endl;
     }
     else
     {
       std::cout << "Card type is not found in context" << std::endl;
     }

     error = ctxGetInt(ctx, PAR_OWN_CARD, &ivalue);
     if (error==ERR_OK)
     {
       std::cout << "Own card = " << ivalue << std::endl;
     }
     else
     {
       std::cout << "Own card is not found in context" << std::endl;
     }

     error = ctxGetInt(ctx, PAR_VAS_LENGTH, &ivalue);
     if (error==ERR_OK)
     {
       std::cout << "vas xml length = " << ivalue << std::endl;

       char* vas=new char [ivalue+1];
       error = ctxGetString(ctx, PAR_VAS_STRING, vas, ivalue+1);
       if (error == ERR_OK)
       {
        std::cout << "vas xml string " << std::endl << vas << std::endl;
       }
       else
       {
         std::cout << "vas xml string is not found in context" << std::endl;
       }
       delete [] vas;
     }
     else
     {
       std::cout << "vas length is not found in context" << std::endl;
     }
   }
   ctxFree(ctx);
@endcode


  Существут два способа прередать хэш функции ::card_authorize15:
  -# В поле ::auth_answer15::Hash. Значение передается в виде ASCII строки. Если хэш получен вызовом функции ::ReadCardContext, то первый символ 'H' должен быть удален.
  -# В аргументе Track2. Значение передается "как есть". Библиотека pilot_nt сама удалит начальный символ 'H'.


  Передача хэша в аргументе track2:
@code{.cpp}
    auth_answer14 argument;
    DWORD amount1 = 99900;

    memset(&argument, 0, sizeof(argument));
    //allocate context
    CONTEXT_PTR ctx=ctxAlloc();

    argument.ans.TType = OP_PURCHASE;
    argument.ans.Amount = amount1;

    //предполагаем, что хэш мы получили предыдущим вызовом ReadCardContext
    result = card_authorize15(hashFromReadCard.c_str(), &argument, NULL, 0, ctx);

    //Не забываем освободить поле auth_answer::Check
    if (argument.ans.Check)
      ::GlobalFree((HGLOBAL)argument.ans.Check);

    ctxFree(ctx);

@endcode

  Передача хэша в поле Hash:
@code{.cpp}
    auth_answer14 argument;
    DWORD amount1 = 99900;

    memset(&argument, 0, sizeof(argument));
    //allocate context
    CONTEXT_PTR ctx=ctxAlloc();

    argument.ans.TType = OP_PURCHASE;
    argument.ans.Amount = amount1;

    //предполагаем, что хэш мы получили предыдущим вызовом ReadCardContext
    //set hash, skiping the first 'H'
    strcpy(argument.Hash, hashFromReadCard.c_str()+1);
    result = card_authorize15(NULL, &argument, NULL, 0, ctx);

    //Не забываем освободить поле auth_answer::Check
    if (argument.ans.Check)
      ::GlobalFree((HGLOBAL)argument.ans.Check);

    ctxFree(ctx);

@endcode

  Пример проверки причины получения результата 4353:
@code{.cpp}
    if (result == 4353)
    {

      //check the reason for the response code 4353
      //It can be: 
      //1. The card was issued by Sberbank. 
      //2. The card corresponds to some kind of loyalty program. 
      //3. Was read the GooglePay VAS 
      
      //check that the vas is present in response
      int length=0;
      result = ctxGetInt(ctx, PAR_VAS_LENGTH, &length);
      if (result==ERR_OK && length)
      {
        std::cout << "Vas found in response. length = %d" << length << std::endl;
        char* vas=new char[length+1];
        result = ctxGetString(ctx, PAR_VAS_STRING, vas, length+1);
        if (result==ERR_OK)
        {
          std::cout << "vas xml string " << std::endl << vas << std::endl;
        }
        delete [] vas;
      }

      //Check card issuer

      hash = std::string(argument.Hash);

      if (argument.SberOwnCard)
      {
        std::cout << "Card was issued by Sberbank. argument.SberOwnCard=" << argument.SberOwnCard<< std::endl;
        std::cout << "Using an external library and the hash ";
        std::cout << hash.c_str() << " we can query the balance and to write off the Spasibo bonuses"<<std::endl;
      }
      else
      {
        std::cout << "This card was issued by third-party bank. argument.SberOwnCard=" << argument.SberOwnCard<< std::endl;
      }

      //check the loyalty card. In general, it can be a bank card of Sberbank with loyalty data   
      int lltId=0;
      result = ctxGetInt(ctx, PAR_LLT_ID, &lltId);
      if (result==ERR_OK && lltId)
      {
        std::cout << "Loyalty programm number = " << lltId << std::endl;
        std::cout << "Loyalty value = " << argument.Track3 << std::endl;
      }
      else
      {
        std::cout << "Loyalty not found" << std::endl;
      }
 
      //some other code...
    }
@endcode
  @see Docs\Для разработчиков ПО ККМ\\examples\\pilot_nt.dll\\cpp\\vas
*/
/** @addtogroup FEATURE_ADD_TICKETS Передача номеров билетов Аэрофлота на терминал для дальнейшей отправки на банковский хост

  Для передачи номеров билетов необходимо использовать функцию ::card_authorize6_ext, поскольку в ней присутствуют необходимые аргументы.

  Пример передачи номеров билетов на терминал:
@code{.cpp}
  typedef int (*dynamic_card_auth6_ext)(char *track2, auth_answer6 *auth_answer, payment_info_item *payinfo);
  dynamic_card_auth6_ext card_auth;
  payment_info_item infoItem;
  auth_answer6 argument;

  memset(&infoItem, 0, sizeof(infoItem));
  memset(&argument, 0, sizeof(argument));
  // fill argument
  argument.auth_answ.TType = OP_SEND_TICKETS;
  if (rrn)
  {
    strcpy(argument.RRN, rrn);
  }
  // fill payment info item
  infoItem.dwTag = paymentTag;
  if (tagValue)
  {
    strcpy(infoItem.Value, tagValue);
  }
  infoItem.pNextItem = NULL;

  DWORD result = card_auth(NULL, &argument, &infoItem);
@endcode
  Например: @see Docs\Для разработчиков ПО ККМ\\examples\\pilot_nt.dll\\cpp\\payment-aero
*/
/** @addtogroup FEATURE_PURCHASE_WITH_CASHBACK Операция "Оплата с выдачей наличных"

  Для выполнения на терминале операции "Оплата с выдачей наличных" необходимо использовать функцию ::card_authorize15 и код операции ::OP_PUR_CASHBACK.
  Общая сумма операции передается в поле auth_answer::Amount. Сумма наличных передается во входящем контексте операции в переменной ::PAR_AMOUNT_OTHER в виде целого числа.

  Пример выполнения операции "Оплата с выдачей наличных":
@code{.cpp}
  CONTEXT_PTR ctx = NULL;
  try
  {
    auth_answer14 argument;
    DWORD amount = 10000;
    DWORD amountOther = 50000;
    DWORD amountFull = amount + amountOther;
    DWORD result;

    memset(&argument, 0, sizeof(argument));
    argument.ans.TType = OP_PUR_CASHBACK;
    argument.ans.Amount = amountFull;
    //allocate context
    CONTEXT_PTR ctx = ctxAlloc();
    ctxSetInt(ctx, PAR_AMOUNT_OTHER, amountOther);
    result = card_authorize15(NULL, &argument, NULL, ctx, 0);
    std::cout << "Operation completed with code '" << result << "'!" << std::endl;
  }
  catch (...)
  {
  }

  ctxFree(ctx);
@endcode
  Например: @see Docs\Для разработчиков ПО ККМ\\examples\\pilot_nt.dll\\cpp\\purchase-with-cashback
*/
/** @addtogroup FEATURE_CASH_ON_TRADE Операция "Выдача наличных в ТСТ"

  Для выполнения на терминале операции "Выдача наличных в ТСТ" необходимо использовать функцию ::card_authorize15 и код операции ::OP_CASH_ON_TRADE.

  Пример выполнения операции "Выдача наличных в ТСТ":
@code{.cpp}
  try
  {
    auth_answer14 argument;
    DWORD amount = 40000;
    DWORD result;

    memset(&argument, 0, sizeof(argument));
    argument.ans.TType = OP_CASH_ON_TRADE;
    argument.ans.Amount = amount;

    result = card_authorize15(NULL, &argument, NULL, 0, 0);
    std::cout << "Operation completed with code '" << result << "'!" << std::endl;
  }
  catch (...)
  {
  }
@endcode
  Например: @see Docs\Для разработчиков ПО ККМ\\examples\\pilot_nt.dll\\cpp\\cash-trade
*/

/** @addtogroup FEATURE_ASK_CARDHOLDER_ABOUT Ввод текста на пинпаде

  Для ввода текста на пинпаде должна использоваться функция ::AskCardHolderAbout. 
  @note Ввод пользователя на пинпаде выполняется в открытом виде, введенные символы не маскируются звездочками.
*/

#pragma pack(1)

/** Идентификатор контекста операции */
typedef long CONTEXT_PTR;

/** Идентификаторы параметров, которые можно получить или передать через контекст операции */
typedef enum {
PAR_LLT_ID          = 1,    ///< [out] Номер программы лояльности в который попала карта, целое. Параметр возвращается при вызове функций ::card_authorize15 и ::ReadCardContext
PAR_PAN             = 2,    ///< [out] Маскированный номер карты, строка. Параметр возвращается при вызове функций ::ReadCardContext
PAR_HASH            = 3,    ///< [out] Хэш. Строка. Параметр возвращается функцией ::ReadCardContext
PAR_CARD_TYPE       = 4,    ///< [in/out] Тип карты. Перечисление ::CardTypes. Параметр используется функциями ::ReadCardContext и ::card_authorize15 в качестве входного для управления чтением VAS и ::ReadCardContext в качестве выходного параметра. 
PAR_OWN_CARD        = 5,    ///< [out] Признак "Карта выпущена Сбербанком". Целое. Параметр возвращается функцией ::ReadCardContext
PAR_VAS_LENGTH      = 6,    ///< [out] Длина строки с xml данными VAS без учета завершающего ноля. Целое. Параметр возвращается функцией ::ReadCardContext и ::card_authorize15
PAR_VAS_STRING      = 7,    ///< [out] Строка с xml данными VAS. Строка. Параметр возвращается функцией ::ReadCardContext и ::card_authorize15
PAR_ENCRYPTED_DATA  = 8,    ///< [in/out] Шифрованный номер карты и срок действия. Бинарное значение. Возвращается функцией ::card_authorize15 и для нее же может использоваться в качестве входного параметра. Если шифрованные данные передаются через аргумент track2, то данные должны быть дополнены символом 'E' слева и после следует бинарное значение. Не реализован для протокола ТТК. @see ::auth_answer8
PAR_LLT_DATA        = 9,    ///< [out] Считанные с карты данные лояльности. Возвращается функцией ::ReadCardContext
PAR_AMOUNT_OTHER    = 10,   ///< [in] Дополнительная сумма транзакции (значение EMV тега 9F03 или SmartVista тега DF50)
PAR_REALPAN         = 11    ///< [out] 
} EParameterName;



/**
 * @defgroup FINANCIAL Финансовые операции pilot_nt.dll
   @ingroup DOCUMENT_NAME
 */
/**@{*/

/** Типы операций */
typedef enum {
OP_PURCHASE     = 1,   ///< Оплата покупки
OP_CASH         = 2,   ///< Выдача наличных (только ВСП)
OP_RETURN       = 3,   ///< Возврат либо отмена покупки
OP_BALANCE      = 4,   ///< Баланс (только ВСП)
OP_FUNDS        = 6,   ///< Безнал.перевод (только ВСП)
OP_CANCEL       = 8,   ///< Отмена покупки. Библиотека не разделяет отмену и возврат и всегда выполняет возврат. Для выполнения только отмены, в файле pinpad.ini должен быть указан параметр PilotNtSeparateCancelAndRefund=1
OP_ADD_AUTH     = 42,  ///< Добавочная предавторизация
OP_CANC_AUTH    = 43,  ///< Отмена предавторизации
OP_PREAUTH      = 51,  ///< Предавторизация
OP_COMPLETION   = 52,  ///< Завершение расчета
OP_CASHIN       = 53,  ///< Взнос наличных (только ВСП)
OP_CASHIN_COMP  = 54,  ///< Подтверждение взноса (только ВСП)
OP_PILOT_START  = 55,  ///< Операция зарезервирована и не должна использоваться
OP_PILOT_STATUS = 56,  ///< Операция зарезервирована и не должна использоваться
OP_PILOT_STOP   = 57,  ///< Операция зарезервирована и не должна использоваться
OP_SETPIN       = 58,  ///< Установка ПИНа (только ВСП)
OP_CHANGEPIN    = 59,  ///< Смена ПИНа (только ВСП)
OP_SEND_TICKETS = 60,  ///< Передача номеров билетов (Аэрофлот)
OP_PUR_CASHBACK = 61,  ///< Оплата покупки с выдачей наличных
OP_CASH_ON_TRADE= 62,  ///< Выдача наличных в торговых точках
OP_RFU_CANCEL   = 63   ///< Отмена покупки. !!!Номер операции конфликтует с таким же кодом операции U2!!! !!!Не использовать!!! Операция удалена в версии 31.00 и в будущем будет синхронизирована с U2
} OperationTypes;

#define OpetationTypes OperationTypes //fix spelling error with backward compatibility

/**
 * Основные параметры операции.
 * Структура, используемая для описания операции и получения результатов выполнения операции.
 */
/** @struct auth_answer
 *  @brief Основные параметры операции.
 */
 typedef struct {
   int TType;             /**< [in] тип операции. см ::OpetationTypes */
   unsigned long Amount;  /**< [in] сумма в копейках                    */
   char RCode[3];         /**< [out] двузначный код результата авторизации. Значение 00 означает успех операции, 01-98 - полученные от хоста ошибки авторизации, 99 - все остальные ошибки, в том числе возникшие локально и не свзанные с ответами хоста.*/
   char AMessage[16];     /**< [out] текст результата авторизации       */
   int  CType;            /**< [in,out] тип карты                       */
   char* Check;           /**< [out] образ чека, должен освобождаться GlobalFree в вызывающей программе */
} auth_answer;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer Основные параметры операции. См. ::auth_answer
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize)(char *track2,  auth_answer *auth_answer);
extern fcard_authorize card_authorize;
#else
PILOT_NT_API int  card_authorize(char *track2,  auth_answer *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/
/** @struct auth_answer2
 *  @brief Расширение для получения кода авторизации успешной операции.
 */
typedef struct {
  auth_answer auth_answ;  /**< [in]  Основные параметры операции. См. ::auth_answer */
  char AuthCode[MAX_AUTHCODE];  /**< [out] Код авторизации. 7 байт.              */
} auth_answer2;

/** @brief Выполнение операций по картам
 *  @param[out] track2 - данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer - см. ::auth_answer2
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize2)(char *track2,  auth_answer2 *auth_answer);
extern fcard_authorize2 card_authorize2;
#else
PILOT_NT_API int  card_authorize2(char *track2,  auth_answer2 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer3
 *  @brief Расширение для получения кода авторизации успешной операции и номера карты.
 */
typedef struct {
  auth_answer auth_answ; /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char AuthCode[MAX_AUTHCODE]; /**< [out] Код авторизации. 7 байт.                       */
  char CardID[CARD_ID_LEN];     /**< [out] Идентификатор карты. 25 байт. Для международных карт все символы, кроме первых 6 и последних 4, будут заменены символами ‘*’.*/
} auth_answer3;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer3
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize3)(char *track2,  auth_answer3 *auth_answer);
extern fcard_authorize3 card_authorize3;
#else
PILOT_NT_API int  card_authorize3(char *track2,  auth_answer3 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer4
 *  @brief Расширение для получения кода авторизации успешной операции, номера карты, кода ответа, времени операции и номера операции на кассе.
 */
typedef struct {
  auth_answer auth_answ; /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char AuthCode[MAX_AUTHCODE]; /**< [out] Код авторизации. 7 байт.                            */
  char CardID[CARD_ID_LEN];     /**< [out] Идентификатор карты. 25 байт.                       */
  int  ErrorCode;               /**< [out] Код ошибки.                                         */
  char TransDate[TRANSDATE_LEN];/**< [out] Дата и время операции                               */
  int  TransNumber;             /**< [out] Номер операции за опер. день, см. номер на чеке     */
} auth_answer4;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer4
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize4)(char *track2,  auth_answer4 *auth_answer);
extern fcard_authorize4 card_authorize4;
#else
PILOT_NT_API int  card_authorize4(char *track2,  auth_answer4 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer5
 *  @brief Расширение для получения кода авторизации успешной операции и номера ссылки (RRN).
 */
typedef struct {
  auth_answer auth_answ;   /**< [in]  Основные параметры операции. См. ::auth_answer */
  char   RRN[MAX_REFNUM];         /**< [in,out] Номер ссылки операции, присвоенный хостом. Используется
                                                для операций возврат и множественной авторизации.
                                                Содержит уникальный 12-значный ссылочный номер.
                                                При предавторизации это поле является выходным
                                                (его заполняет библиотека pilot_nt.dll), а при
                                                завершении расчета – входным (значение должно 
                                                быть заполнено вызывающей программой; оно должно
                                                совпадать со значением, возвращенным при предавторизации).*/
  char   AuthCode[MAX_AUTHCODE]; /**< [out] Код авторизации. 7 байт.                       */
} auth_answer5;

/** @brief Выполнение операций по картам
 *  @param[out] track2 - данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer - см. ::auth_answer5
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize5)(char *track2,  auth_answer5 *auth_answer);
extern fcard_authorize5 card_authorize5;
#else
PILOT_NT_API int  card_authorize5(char *track2,  auth_answer5 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer6
 *  @brief Расширение для получения данных как при выполнении auth_answer5 и auth_answer4.
 */
typedef struct {
  auth_answer auth_answ;    /**< [in, out]  Основные параметры операции. См. ::auth_answer  */
  char   AuthCode[MAX_AUTHCODE];  /**< [out] Код авторизации. 7 байт.                             */
  char   CardID[CARD_ID_LEN];      /**< [out] Идентификатор карты. 25 байт.                        */
  int    ErrorCode;                /**< [out] Код ошибки.                                          */
  char   TransDate[TRANSDATE_LEN]; /**< [out] Дата и время операции                                */
  int    TransNumber;              /**< [out] Номер операции за опер. день, см. номер на чеке      */
  char   RRN[MAX_REFNUM];          /**< [in,out] Номер ссылки операции, присвоенный хостом. Используется
                                                для операций возврат и множественной авторизации.
                                                Содержит уникальный 12-значный ссылочный номер.
                                                При предавторизации это поле является выходным
                                                (его заполняет библиотека pilot_nt.dll), а при
                                                завершении расчета – входным (значение должно 
                                                быть заполнено вызывающей программой; оно должно
                                                совпадать со значением, возвращенным при предавторизации).*/
} auth_answer6;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer6
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize6)(char *track2,  auth_answer6 *auth_answer);
extern fcard_authorize6 card_authorize6;
#else
PILOT_NT_API int  card_authorize6(char *track2,  auth_answer6 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct payment_info_item
 *  @brief Элемент цепочки тэгов для передачи на сервер платежной системы
 */
typedef struct {
  DWORD  dwTag;                   /**< Тег платежной системы. */
  char   Value[MAX_PAYMENT_ITEM]; /**< Значение тэга платежной системы. 128 байт. ::MAX_PAYMENT_ITEM */
  BYTE   Flags;                   /**< must be 0x40 for immediate sending */
  void*  pNextItem;               /**< Следующий элемент цепочки. В случае NULL, это последний элемент цепочки. */
} payment_info_item;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer6
 *  @param[in,out] payinfo см. ::payment_info_item
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize6_ext)(char *track2,  auth_answer6 *auth_answer,  payment_info_item *payinfo);
extern fcard_authorize6_ext card_authorize6_ext;
#else
PILOT_NT_API int  card_authorize6_ext(
  char *track2,
   auth_answer6 *auth_answer,
   payment_info_item *payinfo
);
#endif /*PILOT_NT_DYNAMIC*/


/** @struct auth_answer7
 *  @brief Расширение для получения кода авторизации успешной операции, номера карты и признака принадлежности карты Сбербанку.
 */
typedef struct {
  auth_answer auth_answ;    /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char   AuthCode[MAX_AUTHCODE];  /**< [out] Код авторизации. 7 байт.                            */
  char   CardID [CARD_ID_LEN];     /**< [out] Идентификатор карты. 25 байт.                       */
  int    SberOwnCard;              /**< [out] Флаг принадлежности карты Сбербанку                 */
} auth_answer7;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer7
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize7)(char *track2,  auth_answer7 *auth_answer);
extern fcard_authorize7 card_authorize7;
#else
PILOT_NT_API int  card_authorize7(char *track2,  auth_answer7 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer8
 *  @brief Расширение для получения данных как при выполнении auth_answer5 и auth_answer4, а также номера карты и срока действия в шифрованном виде.
 */
typedef struct {
  auth_answer auth_answ;      /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char   AuthCode[MAX_AUTHCODE];    /**< [out] Код авторизации. 7 байт.                            */
  char   CardID[CARD_ID_LEN];        /**< [out] Идентификатор карты. 25 байт.                       */
  int    ErrorCode;                  /**< [out] Код ошибки.                                         */
  char   TransDate[TRANSDATE_LEN];   /**< [out] Дата и время операции                               */
  int    TransNumber;                /**< [out] Номер операции за опер. день, см. номер на чеке     */
  char   RRN[MAX_REFNUM];            /**< [in,out] Номер ссылки операции, присвоенный хостом. Используется
                                                для операций возврат и множественной авторизации.
                                                Содержит уникальный 12-значный ссылочный номер.
                                                При предавторизации это поле является выходным
                                                (его заполняет библиотека pilot_nt.dll), а при
                                                завершении расчета – входным (значение должно 
                                                быть заполнено вызывающей программой; оно должно
                                                совпадать со значением, возвращенным при предавторизации).*/
  char   EncryptedData[MAX_ENCR_DATA*2+1]; /**< [in, out] шифрованный номер карты и срок действия. Строка.*/
} auth_answer8;
/** @brief Выполнение операций по картам.
 *  @note Функция удваивает количество воззвращаемых чеков.
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer8
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize8)(char *track2,  auth_answer8 *auth_answer);
extern fcard_authorize8 card_authorize8;
#else
PILOT_NT_API int  card_authorize8(char *track2,  auth_answer8 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct preauth_rec
 *  @brief  Структура для описания одной операции в списке, по которой нужно выполнить завершение расчета.
 */
typedef struct {
  unsigned long  Amount;          /**< [in] сумма в копейках              */
  char   RRN[MAX_REFNUM];         /**< [in,out] Номер ссылки операции, присвоенный хостом. Используется
                                                для операций возврат и множественной авторизации.
                                                Содержит уникальный 12-значный ссылочный номер.
                                                При предавторизации это поле является выходным
                                                (его заполняет библиотека pilot_nt.dll), а при
                                                завершении расчета – входным (значение должно
                                                быть заполнено вызывающей программой; оно должно
                                                совпадать со значением, возвращенным при предавторизации).*/
  char           Last4Digits[5];  /**< [in] последние 4 цифры номера карты*/
  unsigned short ErrorCode;       /**< [out] Код ошибки.                  */
} preauth_rec;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_ans см. ::auth_answer8
 *  @param[in,out] pPreAuthList Массив структур с описанием, по которым требуется выполнить "Завершение расчета". См. ::preauth_rec
 *  @param[in] NumAuths Общее количество операций, по которым требуется выполнить "Завершение расчета".
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_complete_multi_auth8)(char* track2,  auth_answer8* auth_ans,  preauth_rec* pPreAuthList, int NumAuths);
extern fcard_complete_multi_auth8 card_complete_multi_auth8;
#else
PILOT_NT_API int card_complete_multi_auth8(
  char* track2,
   auth_answer8* auth_ans,
   preauth_rec*  pPreAuthList,
  int NumAuths
);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer9
*  @brief Расширение для получения кода авторизации успешной операции, номера карты, хеша номера карты и признака принадлежности карты Сбербанку.
 */
typedef struct {
  auth_answer   ans;                     /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char          AuthCode[MAX_AUTHCODE]; /**< [out] Код авторизации. 7 байт.                            */
  char          CardID [CARD_ID_LEN];    /**< [out] Идентификатор карты. 25 байт.                       */
  int           SberOwnCard;             /**< [out] Флаг принадлежности карты Сбербанку                 */
  char          Hash[CARD_HASH_LEN];     /**< [in, out] хеш SHA1 от номера карты, в формате ASCII с нулевым байтом в конце. 40 байт.*/
} auth_answer9;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer9
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize9)(char *track2,  auth_answer9 *auth_answer);
extern fcard_authorize9 card_authorize9;
#else
PILOT_NT_API int  card_authorize9(char *track2,  auth_answer9 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer10
 *  @brief Расширение для получения данных как при выполнении auth_answer4, а также принадлежности карты Сбербанку
 *  и хеша от номера карты.
 */
typedef struct {
  auth_answer   ans;               /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char   AuthCode[MAX_AUTHCODE];  /**< [out] Код авторизации. 7 байт.              */
  char   CardID[CARD_ID_LEN];      /**< [out] Идентификатор карты. 25 байт. Для международных карт все символы, кроме первых 6 и последних 4, будут заменены символами ‘*’.*/
  int    ErrorCode;                /**< [out] Код ошибки.                                         */
  char   TransDate[TRANSDATE_LEN]; /**< [out] Дата и время операции                               */
  int    TransNumber;              /**< [out] Номер операции за опер. день, см. номер на чеке     */
  int    SberOwnCard;              /**< [out] Флаг принадлежности карты Сбербанку                 */
  char   Hash[CARD_HASH_LEN];      /**< [in, out] хеш от номера карты, в формате ASCII с нулевым байтом в конце*/
} auth_answer10;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer10
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize10)(char *track2,  auth_answer10 *auth_answer);
extern fcard_authorize10 card_authorize10;
#else
PILOT_NT_API int  card_authorize10(char *track2,  auth_answer10 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer11
 *  @brief Расширение для получения кода авторизации успешной операции, номера карты, кода ответа,
 *         даты, времени и номера операции, хеша номера карты, признака принадлежности карты Сбербанку, третьей дорожки карты.
 
 */
typedef struct {
  auth_answer   ans;               /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char   AuthCode[MAX_AUTHCODE];  /**< [out] Код авторизации. 7 байт.              */
  char   CardID[CARD_ID_LEN];      /**< [out] Идентификатор карты. 25 байт. Для международных карт все символы, кроме первых 6 и последних 4, будут заменены символами ‘*’.*/
  int    ErrorCode;                /**< [out] Код ошибки.                                         */
  char   TransDate[TRANSDATE_LEN]; /**< [out] Дата и время операции                               */
  int    TransNumber;              /**< [out] Номер операции за опер. день, см. номер на чеке     */
  int    SberOwnCard;              /**< [out] Флаг принадлежности карты Сбербанку                 */
  char   Hash[CARD_HASH_LEN];      /**< [in, out] хеш SHA1 от номера карты, в формате ASCII с нулевым байтом в конце. 40 байт.*/
  char   Track3[CARD_TRACK3_LEN];  /**< [out] Третья дорожка карты. В PCI DSS решениях содержит данные с карты лояльности*/
  unsigned long RequestID;         /**< [in,out] Уникальный номер операции. Только PCI DSS решения.*/
} auth_answer11;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer11
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize11)(char *track2,  auth_answer11 *auth_answer);
extern fcard_authorize11 card_authorize11;
#else
PILOT_NT_API int  card_authorize11(char *track2,  auth_answer11 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer12
 *  @brief Расширение card_authorize11 возможностью указать номер отдела и задать/получить номер ссылки.
 */
typedef struct  {
  auth_answer   ans;              /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char   AuthCode[MAX_AUTHCODE]; /**< [out] Код авторизации. 7 байт.              */
  char   CardID[CARD_ID_LEN];     /**< [out] Идентификатор карты. 25 байт. Для международных карт все символы, кроме первых 6 и последних 4, будут заменены символами ‘*’.*/
  int    ErrorCode;               /**< [out] Код ошибки.                                         */
  char   TransDate[TRANSDATE_LEN];/**< [out] Дата и время операции                               */
  int    TransNumber;             /**< [out] Номер операции за опер. день, см. номер на чеке     */
  int    SberOwnCard;             /**< [out] Флаг принадлежности карты Сбербанку                 */
  char   Hash[CARD_HASH_LEN];     /**< [in, out] хеш SHA1 от номера карты, в формате ASCII с нулевым байтом в конце. 40 байт.*/
  char   Track3[CARD_TRACK3_LEN]; /**< [out] третья дорожка карты. В PCI DSS решениях содержит данные с карты лояльности*/
  unsigned long RequestID;        /**< [in,out] Уникальный номер операции. Только PCI DSS решения.*/
  DWORD  Department;              /**< [in] Порядковый номер отдела от 0 до 14-ти, включительно.
                                            При установке номера отдела в 0xFFFFFFFF, номер отдела
                                            будет запрошен через интерфейс терминала после вставки карты.
                                            Если номер отдела будет указан вне настроенного диапазона,
                                            то терминал вернет код ошибки 4191. */
  char   RRN[MAX_REFNUM];         /**< [in,out] Номер ссылки операции, присвоенный хостом. Используется
                                                для операций возврат и множественной авторизации.
                                                Содержит уникальный 12-значный ссылочный номер.
                                                При предавторизации это поле является выходным
                                                (его заполняет библиотека pilot_nt.dll), а при
                                                завершении расчета – входным (значение должно 
                                                быть заполнено вызывающей программой; оно должно
                                                совпадать со значением, возвращенным при предавторизации).*/
} auth_answer12;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer12
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize12)(char *track2,  auth_answer12 *auth_answer);
extern fcard_authorize12 card_authorize12;
#else
PILOT_NT_API int  card_authorize12(char *track2,  auth_answer12 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer13
 *  @brief Расширение card_authorize11 возможностью указать номер отдела, код валюты и получить способ чтения карты, имя клиента карты и AID.
 */
typedef struct {

  auth_answer   ans;              /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char   AuthCode[MAX_AUTHCODE]; /**< [out] Код авторизации. 7 байт.                       */
  char   CardID[CARD_ID_LEN];     /**< [out] Идентификатор карты. 25 байт. Для международных карт все символы, кроме первых 6 и последних 4, будут заменены символами ‘*’.*/
  int    ErrorCode;               /**< [out] Код ошибки.                                         */
  char   TransDate[TRANSDATE_LEN];/**< [out] Дата и время операции                               */
  int    TransNumber;             /**< [out] Номер операции за опер. день, см. номер на чеке     */
  int    SberOwnCard;             /**< [out] Флаг принадлежности карты Сбербанку                 */
  char   Hash[CARD_HASH_LEN];     /**< [in, out] хеш SHA1 от номера карты, в формате ASCII с нулевым байтом в конце. 40 байт.*/
  char   Track3[CARD_TRACK3_LEN]; /**< [out] третья дорожка карты. В PCI DSS решениях содержит данные с карты лояльности*/
  DWORD  RequestID;               /**< [in,out] Уникальный номер операции. Только PCI DSS решения.*/
  DWORD  Department;              /**< [in] Порядковый номер отдела от 0 до 14-ти, включительно.
                                            При установке номера отдела в 0xFFFFFFFF, номер отдела
                                            будет запрошен через интерфейс терминала после вставки карты.
                                            Если номер отдела будет указан вне настроенного диапазона,
                                            то терминал вернет код ошибки 4191. */
  char   RRN[MAX_REFNUM];         /**< [in,out] Номер ссылки операции, присвоенный хостом. Используется
                                                для операций возврат и множественной авторизации.
                                                Содержит уникальный 12-значный ссылочный номер.
                                                При предавторизации это поле является выходным
                                                (его заполняет библиотека pilot_nt.dll), а при
                                                завершении расчета – входным (значение должно
                                                быть заполнено вызывающей программой; оно должно
                                                совпадать со значением, возвращенным при предавторизации).*/
  DWORD  CurrencyCode;            /**< [in] Международный код валюты (810, 643, 840, 978 и т.д.) */
  char   CardEntryMode;           /**< [out] Способ чтения карты ('D'-магн.полоса, 'M'-ручной ввод, 'C'-чип, 'E'-бесконтакт EMV, 'R'-бесконтакт magstripe, 'F'-fallback)*/
  char   CardName[MAX_CARD_NAME_LEN]; /**< [out] Название типа карты */
  char   AID[MAX_AID_ASCII_LEN];  /**< [out] Application ID чиповой карты (в виде ASCIIZ-строки)*/
  char   FullErrorText[MAX_FULL_ERROR_TEXT]; /**< [out] Полный текст сообщения об ошибке*/
} auth_answer13;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer13
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize13)(char *track2,  auth_answer13 *auth_answer);
extern fcard_authorize13 card_authorize13;
#else
PILOT_NT_API int  card_authorize13(char *track2,  auth_answer13 *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @struct auth_answer14
 *  @brief Расширение card_authorize13 возможностью указать информацию о товаре.
 */
typedef struct  {
  auth_answer   ans;               /**< [in, out]  Основные параметры операции. См. ::auth_answer */
  char   AuthCode[MAX_AUTHCODE];  /**< [out] Код авторизации. 7 байт.              */
  char   CardID[CARD_ID_LEN];      /**< [out] Идентификатор карты. 25 байт. Для международных карт все символы, кроме первых 6 и последних 4, будут заменены символами ‘*’.*/
  int    ErrorCode;                /**< [out] Код ошибки.                                         */
  char   TransDate[TRANSDATE_LEN]; /**< [out] Дата и время операции                               */
  int    TransNumber;              /**< [out] Номер операции за опер. день, см. номер на чеке     */
  int    SberOwnCard;              /**< [out] Флаг принадлежности карты Сбербанку                 */
  char   Hash[CARD_HASH_LEN];      /**< [in, out] хеш SHA1 от номера карты, в формате ASCII с нулевым байтом в конце. 40 байт.*/
  char   Track3[CARD_TRACK3_LEN];  /**< [out] третья дорожка карты. В PCI DSS решениях содержит данные с карты лояльности*/
  DWORD  RequestID;                /**< [in,out] Уникальный номер операции. Только PCI DSS решения.*/
  DWORD  Department;              /**< [in] Порядковый номер отдела от 0 до 14-ти, включительно.
                                            При установке номера отдела в 0xFFFFFFFF, номер отдела
                                            будет запрошен через интерфейс терминала после вставки карты.
                                            Если номер отдела будет указан вне настроенного диапазона,
                                            то терминал вернет код ошибки 4191. */
  char   RRN[MAX_REFNUM];          /**< [in,out] Номер ссылки операции, присвоенный хостом. Используется
                                                для операций возврат, множественной авторизации и завершения расчета.
                                                Содержит уникальный 12-значный ссылочный номер.
                                                При предавторизации это поле является выходным
                                                (его заполняет библиотека pilot_nt.dll), а при
                                                завершении расчета – входным (значение должно
                                                быть заполнено вызывающей программой; оно должно
                                                совпадать со значением, возвращенным при предавторизации).*/
  DWORD  CurrencyCode;             /**< [in] Международный код валюты (810, 643, 840, 978 и т.д.) */
  char   CardEntryMode;            /**< [out] Способ чтения карты ('D'-магн.полоса, 'M'-ручной ввод, 'C'-чип, 'E'-бесконтакт EMV, 'R'-бесконтакт magstripe, 'F'-fallback)*/
  char   CardName[MAX_CARD_NAME_LEN]; /**< [out] Название типа карты */
  char   AID[MAX_AID_ASCII_LEN];   /**< [out] Application ID чиповой карты (в виде ASCIIZ-строки). Не используется для PCI-DSS решений*/
  char   FullErrorText[MAX_FULL_ERROR_TEXT]; /**< [out] Полный текст сообщения об ошибке*/
  DWORD  GoodsPrice;                /**< [in] Цена за единицу товара, коп (34.99->3499)*/
  DWORD  GoodsVolume;               /**< [in] Количество товара, в тыс. долях (30.234->30234)*/
  char   GoodsCode[MAX_GOODS_CODE+1]; /**< [in] Код товара во внешней системе.*/
  char   GoodsName[MAX_GOODS_NAME]; /**< [in] Наименование товара во внешней системе. Внимание! В структуре auth_answer14 название товара на один символ короче чем в gate.dll TGoodsData. Зафиксируем эту ошибку как стандарт*/
}auth_answer14;

/**@brief Структура для получения результатов запроса к мониторингу.
 *
 */
typedef struct {
   DWORD size;                         /**< [out] Размер?         */
   DWORD MonState;                     /**< [out] Статус          */
   DWORD MonMessageType;               /**< [out] Тип             */
   char  MonMessage[MAX_MON_MSG];      /**< [out] Текст сообщения */
}host_status_answer;

/**@brief Структура для запроса статуса операции RequestId.
 *
 */
 typedef struct {
  DWORD size;                      /**< [out] Размер         */
  DWORD RequestId;             /**< [out] Статус операции RequestId    */
}StatusRequestQuery;

/**@brief Структура для получения чека по статусу операции RequestId.
 *
 */
typedef struct {
  DWORD size;                        /**< [out] Размер         */
  char* Cheque;                     /**< [out] Чек исходной операции         */
}StatusRequestResult;

/** @brief Выполнение операций по картам
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer14
 *  @param[in,out] payinfo Информация для платежной системы
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize14)(const char *track2,  auth_answer14 *auth_answer,  payment_info_item *payinfo);
extern fcard_authorize14 card_authorize14;
#else
PILOT_NT_API int  card_authorize14(
  const char *track2,
   auth_answer14 *auth_answer,
   payment_info_item *payinfo
);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Выполнение операций по картам
 *  @note Функция дополнительно принимает входной и выходной контексты операции. Во входном контексте в библиотеку передаются дополнительные параметры операции
 *  в выходном контексте возвращается расширенный результат операции. Параметры, которые могут переданы или получены через контекст операции
 *  перечислены в EParameterName.
 *  @param[in] track2 данные дорожки карты с магнитной полосой. Если NULL, то будет предложено считать карту.
 *  @param[in,out] auth_answer см. ::auth_answer14
 *  @param[in,out] payinfo Информация для платежной системы
 *  @param[in] dataIn см. ::ctxAlloc
 *  @param[in] dataOut см. ::ctxAlloc
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fcard_authorize15)(const char *track2,  auth_answer14 *auth_answer,  payment_info_item *payinfo, CONTEXT_PTR dataIn, CONTEXT_PTR dataOut);
extern fcard_authorize15 card_authorize15;
#else
PILOT_NT_API int  card_authorize15(
  const char *track2,
   auth_answer14 *auth_answer,
   payment_info_item *payinfo,
  CONTEXT_PTR dataIn,
  CONTEXT_PTR dataOut
);
#endif /*PILOT_NT_DYNAMIC*/

/**@}*/

/**
 * @defgroup SERVICE Служебные операции pilot_nt.dll
   @ingroup DOCUMENT_NAME
 */
/**@{*/

 /** @brief Получить номер терминала как строку
 *  @note Функция не поддерживается по протоколу TTK для PCI-DSS решений.
 *  @note Функция возвращает номер терминала, заданный в разделе "Общие настройки", при отсутствии параметра (номера терминалов только в отделах) будет возвращена ошибка 13.
 *  @param[out] pTerminalID Строковое представление номера терминала. 9 байт.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fGetTerminalID)(char* pTerminalID);
extern fGetTerminalID GetTerminalID;
#else
PILOT_NT_API int GetTerminalID(char* pTerminalID);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Открыть в техническое меню на пинпаде
 *  @note По завершении поле auth_answer.Check может содержать образ документа для печати.
 *  @param[out] auth_answer Буфер результата операции
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fServiceMenu)( auth_answer *auth_answer);
extern fServiceMenu ServiceMenu;
#else
PILOT_NT_API int ServiceMenu( auth_answer *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Закрытие дня.
 *  @note  Поля TType, Amount, CType заполнять не нужно.
 *  @param[in,out] auth_answer см. ::auth_answer
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fclose_day)( auth_answer *auth_answer);
extern fclose_day close_day;
#else
PILOT_NT_API int close_day( auth_answer *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Закрытие дня.
 *  @note  Поля auth_answer::Amount, auth_answer::CType и auth_answer::TType заполнять не нужно. После выполнения функции поле auth_answer::Cheque может cодержать образ отчета по картам. Если значение поля не NULL, вызывающая программа должна напечатать возвращенный образ чека, а затем освободить вызовом функции GlobalFree().
    @param[in,out] auth_answer см. ::auth_answer
    @param[in,out] iParams Дополнительная информация для передачи на хост Сбербанка (например, о наличном обороте кассы за смену). В текущей версии поддерживается следующий формат строки:
    1;число_оплат_за_наличные;сумма_оплат_за_наличные;номер кассовой смены
    Число 1 указывает, что следующие два параметра содержат количество наличных платежей и их сумму в копейках.
    Пример: «1;55;20010000;2334» - означает, что за смену было 55 оплат наличными на общую сумму 200100.00 руб, номер кассовой смены 2334.
    Параметр номер смены ккм используется для контроля уникальности, если в течении смены выполнялось несколько сверок итогов.
    @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fclose_day_info)( auth_answer *auth_answer, const char* iParams);
extern fclose_day_info close_day_info;
#else
PILOT_NT_API int close_day_info( auth_answer *auth_answer, const char* iParams);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Получение текущего отчета за текущую смену
 *  @param[in, out] auth_answer См. auth_answer. При значении поля TType = 0 формируется полный отчет, иначе - краткий
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fget_statistics)( auth_answer *auth_answer);
extern fget_statistics get_statistics;
#else
PILOT_NT_API int get_statistics( auth_answer *auth_answer);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Получение номера версии библиотеки pilot_nt.dll
 *  @return Версия как целое число в формате 0x00VVRRBB. VV - версия, RR - релиз, BB - сборка
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fGetVer)();
extern fGetVer GetVer;
#else
PILOT_NT_API unsigned int GetVer();
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Установить конфигурационные параметры в pinpad.ini
 *  @param[in] pConfData Строка формата param1=value1;...paramN=valueN;
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fSetConfigData)(const char* pConfData);
extern fSetConfigData SetConfigData;
#else
PILOT_NT_API int SetConfigData(const char* pConfData);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Деинициализация библиотеки pilot_nt.dll
 *  @note Выполняется отключение от библиотеки gate.dll
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fDone)();
extern fDone Done;
#else
PILOT_NT_API void Done();
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Асинхронное включение чтения карты
 *  @param[in] hDestWindow Хендл окна, которое будет получать сообщения о чтении карты
 *  @param[in] message Идентификатор сообщение о чтении карты
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fEnableReader)(HWND hDestWindow, UINT message);
extern fEnableReader EnableReader;
#else
PILOT_NT_API int EnableReader (HWND hDestWindow, UINT message);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Асинхронное выключение чтения карты
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fDisableReader)();
extern fDisableReader DisableReader;
#else
PILOT_NT_API int DisableReader();
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Проверка готовности пинпада
 *  @note Функция проверяет наличие пинпада. При успешном выполнении возвращает 0 (пинпад подключен), при неудачном – код ошибки (пинпад не подключен или неисправен).
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fTestPinpad)();
extern fTestPinpad TestPinpad;
#else
PILOT_NT_API int TestPinpad();
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Функция переводит последнюю успешную транзакцию в «подвешенное» состояние. Если транзакция находится в этом состоянии, то при следующем сеансе связи с банком она будет отменена..
 *  @note Функция сверяет переданные извне параметры (сумму и код авторизации) со значениями в последней успешной операции, которая была проведена через библиотеку. Если хотя бы один параметр не совпадает, функция возвращает код ошибки 4140 и не выполняет никаких действий.
 *  @warning Не поддерживается при работе по протоколу ТТК.
 *  @param dwAmount Сумма операции (в копейках)
 *  @param pAuthCode Код авторизации.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fSuspendTrx)(DWORD dwAmount, char* pAuthCode);
extern fSuspendTrx SuspendTrx;
#else
PILOT_NT_API int SuspendTrx (DWORD dwAmount, char* pAuthCode);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Функция возвращает последнюю успешную транзакцию в «нормальное» состояние.
 *  После этого транзакция будет включена в отчет и спроцессирована как успешная.
 *  Перевести ее снова в «подвешенное» состояние будет уже нельзя.
 *  @note Функция сверяет переданные извне параметры (сумму и код авторизации) со
 *  значениями в последней успешной операции, которая была проведена через библиотеку.
 *  Если хотя бы один параметр не совпадает, функция возвращает код ошибки 4140 и не выполняет никаких действий.
 *  @warning Не поддерживается при работе по протоколу ТТК.
 *  @param dwAmount Сумма операции (в копейках)
 *  @param pAuthCode Код авторизации.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fCommitTrx)(DWORD dwAmount, char* pAuthCode);
extern fCommitTrx CommitTrx;
#else
PILOT_NT_API int CommitTrx (DWORD dwAmount, char* pAuthCode);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Функция вызывает немедленную отмену последней успешной операции
 *  @note Операция может быть предварительно возможно, ранее
 *  переведенную в «подвешенное» состояние, хотя это и не обязательно). Если транзакция уже
 *  была возвращена в «нормальное» состояние функцией CommitTrx(), то функция RollbackTrx()
 *  завершится с кодом ошибки 4141, не выполняя никаких действий. Функция сверяет переданные
 *  извне параметры (сумму и код авторизации) со значениями в последней успешной операции,
 *  которая была проведена через библиотеку. Если хотя бы одинпараметр не совпадает, функция
 *  возвращает код ошибки 4140 и не выполняет никаких действий.
 *  @warning Не поддерживается при работе по протоколу ТТК.
 *  @param dwAmount Сумма операции (в копейках)
 *  @param pAuthCode Код авторизации.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fRollbackTrx)(DWORD dwAmount, char* pAuthCode);
extern fRollbackTrx RollbackTrx;
#else
PILOT_NT_API int RollbackTrx(DWORD dwAmount, char* pAuthCode);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Функция прерывает работу функций card_authorizeX()
 *  @note Внешнее ПО может вызвать эту функцию из отдельного треда, чтобы досрочно прекратить выполнение любой из функций card_authorize…(). При этом функция card_authorize…() завершится с кодом ошибки 2000 (операция прервана).
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fAbortTransaction)();
extern fAbortTransaction AbortTransaction;
#else
PILOT_NT_API int AbortTransaction();
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Функция передает в терминал торговый чек
 *  @note Максимальный размер торгового чека 62 КБ. Описание в разделе \ref FEATURE_SEND_CHEQUE_TO_BANK
 *  @param dwQueryRequestID Уникальный идентификатор операции (requestID в ответе финансовой операции)
 *  @param pCheque Указатель на строку с торговым чеком
 *  @warning Используется только в торговых решениях PCI DSS.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fAddMerchantCheque)(DWORD dwQueryRequestID, const char* pCheque);
extern fAddMerchantCheque AddMerchantCheque;
#else
PILOT_NT_API int AddMerchantCheque(DWORD dwQueryRequestID, const char* pCheque);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Задать вопрос держателю карты и получить ответ введенный на клавиатуре пинпада.
     @note Вместо вопроса может использоваться предопределенное значение "phone" для ввода телефонного номера или "email" для ввода адреса электронной почты.
     @param[in] question Вопрос, либо предопреденное значение.
     @param[in,out] answer Ответ владельца карты. Для предопределенных значений может содержать значение по умолчанию, которое будет предложено для редактирования. 
     @param[in] answerLength Длина буфера для ответа. Ответ пользователя копируется в аргумент answer функцией strncpy, поэтому завершающего ноля может и не быть.
     @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fAskCardHolderAbout)(const char* question, char* answer, unsigned answerLength);
extern fAskCardHolderAbout AskCardHolderAbout;
#else
PILOT_NT_API int AskCardHolderAbout(const char* question, char* answer, unsigned answerLength);
#endif /*PILOT_NT_DYNAMIC*/
/**
 * Передается в качестве аргумента для получения номера Merchant и терминала.
 */
/** @struct tag_struct_MerchantID_TeminalId
 *  @brief Передается в качестве аргумента для получения MerchantID и TeminalId.
 */
typedef struct tag_struct_MerchantID_TeminalId{
  char          TermNum[MAX_TERMID];         ///< номер терминала
  char          MerchNum[MAX_MERCHANT_LN+1]; ///< номер мерчанта
} struct_MerchantID_TeminalId;
 /** 
 *  @brief Получение номера MerchantId и TetminalId pilot_nt.dll.
 *  @param MerchantID_TeminalId указатель на структуру, типа tag_struct_MerchantID_TeminalId, куда функция запишит MerchantID и TeminalId, при успешном завершении.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fGetMerchantIdTerminalId)(struct_MerchantID_TeminalId* MerchantID_TeminalId);
extern fGetMerchantIdTerminalId GetMerchantIdTerminalId;
#else
PILOT_NT_API int GetMerchantIdTerminalId(struct_MerchantID_TeminalId* MerchantID_TeminalId);
#endif /*PILOT_NT_DYNAMIC*/

typedef enum{
  IdWithComma=0
}ListFormat;

 /** 
 *  @brief Получение списка программ лояльности.
 *  Данная функция запрашивает список лояльности из терминала и позволяет проверить, что программа с ожидаемым id есть в терминале. При успешной обработке запроса функция вернет код ошибки ERR_OK, 
 *  запишет список лояльности в переданный массив байт и длину получившейся строки без учета завершающего ноля  в параметр length.
 *  При успешной обработке запроса может вернуться длина списка равная нулю, в случае если список лояльности не был загружен в терминал. В случае если переданн массив байт
 *  недостаточного размера, функция вернет ошибку ::ERR_MORE_DATA и в параметре length вернет размер, необходимый для записи списка лольности. length указывает на размер без учета завершающего ноля.
 *  @note Возвращается список значений "Номер программы лояльности для внешней системы" в том порядке, как он задан в настройках. Если значение "Номер программы лояльности для внешней системы" 
 *  для какой-то программы не задано, но сама программа присутвует, в этой позиции списка вернется 0. Вопросы правильности настройки программ лояльности с нужным идентификатором должны решаться организационными мерами.
 *  @param format формат в котором необходимо получить список лояльности.
 *  @param  pDest указатель "С" строку, в которую запишется список лояльности при успешно выполнном запросе. При ошибке ::ERR_MORE_DATA запишется sz-1 символ.
 *  @param sz размер переданного массива байт.
 *  @param length размер списка лояльности, полученного при успешной обработке запроса.
 *  @return int Код ошибки.
 */
 
#ifdef PILOT_NT_DYNAMIC
typedef WORD (*fGetLoyaltyList)(ListFormat format, char* pDest, unsigned sz, unsigned *length);
extern fGetLoyaltyList GetLoyaltyList;
#else
PILOT_NT_API WORD GetLoyaltyList(ListFormat format, char* pDest, unsigned sz, unsigned *length);
#endif /*PILOT_NT_DYNAMIC*/

/**
 * @defgroup READCARD Функции чтения карт библиотеки pilot_nt.dll
   @ingroup DOCUMENT_NAME
 * Семейство функций "Чтение карты" предназначено для получения реквизитов карты без списания денежных средств. Чтобы избежать повторного считывания карты после вызова функций "чтение карты" операция может 
 * быть продолжена путем вызова функции card_authorizeX и передачи хэша в аргументе track2. Если карта была считана бесконтактным образом, терминал потребует еще раз париложить карту, т.к. на момент первого чтения карты
 * не были известны сумма и валюта операции, которые являются критичными для проведения операции по бесконтактной карте.
 * Данные функции являются устаревшими и не должны использоваться. Для получения реквизитов операции должен использоваться механизм возврата промежуточного кода ошибки 4353. 
 */
/**@{*/
/** @brief Чтение карты. 
 *  @note Возвращеный хэш не может использоваться для проведения операции в PCI-DSS решениях. Функция возвращает первые 24 символа от строкового представления хэш добавляя 'H' в начале. По это причине функция не может использоваться в PCI-DSS решениях. @see Docs\Для разработчиков ПО ККМ\\examples\\pilot_nt.dll\\cpp\\readcard
 *  @param Last4Digits Буфер, куда функция записывает четыре последних цифры номера карты. Размер буфера должен быть не менее 5 байт.
 *  @param Hash Хеш от номера карты, в формате ASCII с нулевым байтом в конце и первым символом 'H'. Возврщается первые 12 байт хэш (24 символа ascii + 'H'). Размер буфера должен быть не менее 26 байт.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadCard)(char *Last4Digits, char *Hash);
extern fReadCard ReadCard;
#else
PILOT_NT_API int ReadCard  (char *Last4Digits, char *Hash);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Функция позволяет прочитать банковскую карту для использования в скидочной системе «Спасибо от Сбербанка».
 *  @note Карта должна быть выдана Сбербанком, в противном случае функция вернет ошибку 4180.
 *  @param Last4Digits Буфер, куда функция записывает четыре последних цифры номера карты. Размер буфера должен быть не менее 5 байт.
 *  @param Hash Хеш от номера карты, в формате ASCII с нулевым байтом в конце и первым символом 'H'. Размер буфера должен быть не менее 42 байта.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadCardSB)(char *Last4Digits, char *Hash);
extern fReadCardSB ReadCardSB;
#else
PILOT_NT_API int ReadCardSB(char *Last4Digits, char *Hash);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение карты
 *  @param Last4Digits Буфер, куда функция записывает четыре последних цифры номера карты. Размер буфера должен быть не менее 5 байт.
 *  @param Hash Хеш от номера карты, в формате ASCII с нулевым байтом в конце и первым символом 'H'. Размер буфера должен быть не менее 41 байта.
 *  @param pCardType Тип карты. См. ::CardTypes
 *  @param pIsOwnCard Признак "Карта выпущена Сбербанком"
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadCardWithType)(char *Last4Digits, char *Hash, int*  pCardType, int*  pIsOwnCard);
extern fReadCardWithType ReadCardWithType;
#else
PILOT_NT_API int ReadCardWithType(
  char *Last4Digits,
  char *Hash,
  int*  pCardType,
  int*  pIsOwnCard
);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение карты
 *  @param PAN Буфер, куда функция записывает PAN карты
 *  @param Hash Хеш от номера карты, в формате ASCII с нулевым байтом в конце и первым символом 'H'. Размер буфера должен быть не менее 42 байта.
 *  @param pCardType Тип карты. См. ::CardTypes
 *  @param pIsOwnCard Признак "Карта выпущена Сбербанком"
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadMaskedCardWithType)(char *PAN, char *Hash, int*  pCardType, int*  pIsOwnCard);
extern fReadMaskedCardWithType ReadMaskedCardWithType;
#else
PILOT_NT_API int ReadMaskedCardWithType(
  char *PAN,
  char *Hash,
  int*  pCardType,
  int*  pIsOwnCard
);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение полной второй дорожки карты
 *  @note  Данные второй дорожки могут иметь длину до 40 символов.
 *  Вторая дорожка имеет формат:
 *    nnnn...nn=yymmddd...d
 *  где     '=' - символ-разделитель
 *      nnn...n - номер карты
 *      yymm    - срок действия карты (ГГММ)
 *      ddd...d - служебные данные карты
 *  PCI-DSS решения в аргументе Track2 возвращают маскированный номер карты.
 *  @param[out] Track2 Буфер на 41 байт.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadTrack2)(char *Track2);
extern fReadTrack2 ReadTrack2;
#else
PILOT_NT_API int ReadTrack2(char *Track2);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение полной третьей дорожки карты
 *  @note Данные третьей дорожки могут иметь длину до 109 символов.
 *  @param[out] Last4Digits 4 последние цифры карты
 *  @param[out] Hash Хеш от номера карты, в формате ASCII с нулевым байтом в конце и первым символом 'H'. Размер буфера должен быть не менее 42 байта.
 *  @param[out] pTrack3 третья дорожка карты
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadCardTrack3)(char *Last4Digits, char *Hash, char* pTrack3);
extern fReadCardTrack3 ReadCardTrack3;
#else
PILOT_NT_API int ReadCardTrack3(char *Last4Digits, char *Hash, char* pTrack3);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение карты Сберкарт
 *  @param[out] CardNo полный номер карты. Для pci-dss решений возвращается маскированный номер.
 *  @param[out] ClientName имя фамилия клиента эмброссированные на карте
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadSbercard)(char *CardNo, char* ClientName);
extern fReadSbercard ReadSbercard;
#else
PILOT_NT_API int ReadSbercard(char *CardNo, char* ClientName);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение карты
 *  @note Фамилия клиента не возвращается для PCI-DSS решений.
 *  @param[out] pTrack2 Track2
 *  @param[out] ValidThru Срок действия карты в формате YYMM
 *  @param[out] pName имя фамилия клиента эмброссированные на карте.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadCardAndName)(char *pTrack2, char* ValidThru, char* pName);
extern fReadCardAndName ReadCardAndName;
#else
PILOT_NT_API int ReadCardAndName(
  char *pTrack2,
  char* ValidThru,
  char* pName
);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение карты
 *  @note  Чтобы использовать результат для авторизации, их нужно будет сформатировать так "CardNo=ValidThru".  
 *  @note  Функция не поддерживается по протоколу TTK для PCI-DSS решений.
 *  @note  PCI-DSS решения возращают маскированный номер карты.
 *  @param CardNo Номер карты. Может иметь длину от 13 до 19 цифр.
 *  @param ValidThru Срок действия карты в формате YYMM
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadCardFull)(char *CardNo, char *ValidThru);
extern fReadCardFull ReadCardFull;
#else
PILOT_NT_API int ReadCardFull(char *CardNo, char *ValidThru);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Чтение карты
 *  Если требуется чтение нестандартных карт, например карт лояльности на базе Mifare или Google VAS, в контекст операции должен быть передан соответсвующий тип карты. @see ::CardTypes
 *  @param dataOut Контекст операции, в которую копируются pan, хэш, тип карты, признак "Карта выпущена Сбербанком", номер программы лояльности, признаки считывания VAS и т.п.
 *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fReadCardContext)(CONTEXT_PTR dataOut);
extern fReadCardContext ReadCardContext;
#else
PILOT_NT_API int ReadCardContext(CONTEXT_PTR dataOut);
#endif /*PILOT_NT_DYNAMIC*/

/**@}*/

/**
 * @defgroup VENDING Вендинговые операции pilot_nt.dll
   @ingroup DOCUMENT_NAME
 */
/**@{*/
 /** @brief Установить элементы для вывода на экран
 *  @param[in] hText Элемент вывода текста.
 *  @param[in] hEdit Элемент ввода текста.
 *  @return int Код ошибки.
 */

#ifdef PILOT_NT_DYNAMIC
typedef int (*fSetGUIHandles)(int hText, int hEdit);
extern fSetGUIHandles SetGUIHandles;
#else
PILOT_NT_API int SetGUIHandles(int hText, int hEdit);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Извлечь карту. Команда 5020.
*  @return int Код ошибки.
*/
#ifdef PILOT_NT_DYNAMIC
typedef int (*fEjectCard)();
extern fEjectCard EjectCard;
#else
PILOT_NT_API int EjectCard();
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Запрос статуса операции по RequestId
  *  @param[in] query см структуру StatusRequestQuery.
  *  @param[out] result см. структуру StatusRequestResult.
  *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fGetOperationStatusByRequestId)(StatusRequestQuery* query, StatusRequestResult* result);
extern fGetOperationStatusByRequestId GetOperationStatusByRequestId;
#else
PILOT_NT_API int GetOperationStatusByRequestId(StatusRequestQuery* query, StatusRequestResult* result);
#endif /*PILOT_NT_DYNAMIC*/


 /** @brief Чтение ответа сообщения мониторинга
  *  @param[in] hostType Может иметь значения "1" для мониторинга HELIOS или "2" для мониторинга PSDB.
  *  @param[out] host_answ см. структуру host_status_answer
  *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fPilotGetHostStatus)(int hostType,  host_status_answer *host_answ);
extern fPilotGetHostStatus PilotGetHostStatus;
#else
PILOT_NT_API int PilotGetHostStatus(int hostType,  host_status_answer *host_answ);
#endif /*PILOT_NT_DYNAMIC*/

/** @brief Выполнить операцию CloseReader для сброса заставки ожидания на пинпаде (sb_pilot 31)
 *  @return int Возвращает код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fPilotCloseReader)();
extern fPilotCloseReader PilotCloseReader;
#else
PILOT_NT_API int PilotCloseReader();
#endif /*PILOT_NT_DYNAMIC*/

/**@}*/

/**
 * @defgroup CONTEXT Функции работы с контекстом pilot_nt.dll
   @ingroup DOCUMENT_NAME
 */
/**@{*/
 /** @brief Создать контекст операции. Функция создает пустой контекст операции.
  *  @note Для входного контекста значения параметров устанавливаются вызывающей программой, для выходного контекста значения параметров устанавливаются библиотекой.
  *  При повторном использовании контекста, если переменная уже есть в контексте, она будет перезаписана. Рекомендуется либо создавать и удалять контексты при каждой
  *  операции, либо очищать контекст вызовом функции ctxClear перед повторным использованием.
  *  @return CONTEXT_PTR Идентификатор контекста операции или 0, если произошла ошибка
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxAlloc)();
extern fctxAlloc ctxAlloc;
#else
PILOT_NT_API CONTEXT_PTR ctxAlloc(void);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Удалить контекст операции
  *  @param[in] ctx Идентификатор контекста.
  *  @return нет
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxFree)(CONTEXT_PTR ctx);
extern fctxFree ctxFree;
#else
PILOT_NT_API void ctxFree(CONTEXT_PTR ctx);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Отчистить контекст. Функция удаляет все параметры из контекста.
  *  @param[in] ctx Идентификатор контекста.
  *  @return нет
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxClear)(CONTEXT_PTR ctx);
extern fctxClear ctxClear;
#else
PILOT_NT_API void ctxClear(CONTEXT_PTR ctx);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Записать в контекст значение строкового параметра.
  *  @param[in] ctx  Идентификатор контекста.
  *  @param[in] name Идентификатор параметра.
  *  @param[in] str  Указатель на строку.
  *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxSetString)(CONTEXT_PTR ctx, EParameterName name, const char* str);
extern fctxSetString ctxSetString;
#else
PILOT_NT_API int ctxSetString(CONTEXT_PTR ctx, EParameterName name, const char* str);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Записать в контекст значение целочисленного параметра.
  *  @param[in] ctx  Идентификатор контекста.
  *  @param[in] name Идентификатор параметра.
  *  @param[in] val  Значение параметра.
  *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxSetInt)(CONTEXT_PTR ctx, EParameterName name, int val);
extern fctxSetInt ctxSetInt;
#else
PILOT_NT_API int ctxSetInt(CONTEXT_PTR ctx, EParameterName name, int val);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Записать в контекст значение параметра в виде последовательности байт.
  *  @param[in] ctx  Идентификатор контекста.
  *  @param[in] name Идентификатор параметра.
  *  @param[in] val  Указатель на буфер.
  *  @param[in] sz   Длина буфера.
  *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxSetBinary)(CONTEXT_PTR ctx, EParameterName name, unsigned char* val, int sz);
extern fctxSetBinary ctxSetBinary;
#else
PILOT_NT_API int ctxSetBinary(CONTEXT_PTR ctx, EParameterName name, unsigned char* val, int sz);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Считать из контекста значение переменной в виде строки.
  *  @note Для целочисленной переменной вы получите ее строковое представление, а для последовательности байт функция вернет hex строку.
  *  Если размер буфера недостачен, в переменную pVal будет скопировано sz-1 байт + завершающий ноль, а вызов завершится ошибкой ERR_CTX_GET.
  *  @param[in] ctx  Идентификатор контекста.
  *  @param[in] name Идентификатор параметра.
  *  @param[in] val  Указатель на строку.
  *  @param[in] sz   Максимально возможная длина строки.
  *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxGetString)(CONTEXT_PTR ctx, EParameterName name, char* str, int sz);
extern fctxGetString ctxGetString;
#else
PILOT_NT_API int ctxGetString(CONTEXT_PTR ctx, EParameterName name, char* str, int sz);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Считать из контекста значение переменной в виде целого числа.
  *  @note Для строковой переменной будет выполнено преобразование строки в число, для последовательности байт
  *  функция преобразует первые четыре байта последовательности в целое число с прямым порядком байт. 
  *  При возвращении ошибки значение *pVal не изменяется
  *  @param[in] ctx  Идентификатор контекста.
  *  @param[in] name Идентификатор параметра.
  *  @param[in] pVal Указатель на число.
  *  @return int Код ошибки. ERR_OK - переменная считана успешно. ERR_CTX_GET - ошибка получения переменной.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxGetInt)(CONTEXT_PTR ctx, EParameterName name, int* pVal);
extern fctxGetInt ctxGetInt;
#else
PILOT_NT_API int ctxGetInt   (CONTEXT_PTR ctx, EParameterName name, int* pVal);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Считать из контекста значение переменной в виде последовательности байт.
  *  @note Для строковой переменной будет значение будет возвращено без изменения, для целочисленной переменной функция
  *  вернет последовательность из четырех байт с прямым порядком байт. Если размер буфера недостачен, 
  *  в переменную pVal будет скопировано MAXSIZE байт, а вызов завершится ошибкой ERR_CTX_GET.
  *  @param[in] ctx     Идентификатор контекста.
  *  @param[in] name    Идентификатор параметра.
  *  @param[in] pVal    Указатель на буфер результата.
  *  @param[in] pOutSz  Количество байт, скопированных в буфер.
  *  @param[in] MAXSIZE Максимально возможное количество байт.
  *  @return int Код ошибки. ERR_OK - переменная считана успешно. ERR_CTX_GET - ошибка получения переменной.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fctxGetBinary)(CONTEXT_PTR ctx, EParameterName name, unsigned char* pVal, int* pOutSz, int MAXSIZE);
extern fctxGetBinary ctxGetBinary;
#else
PILOT_NT_API int ctxGetBinary(CONTEXT_PTR ctx, EParameterName name, unsigned char* pVal, int* pOutSz, int MAXSIZE);
#endif /*PILOT_NT_DYNAMIC*/

 /** @brief Показать на дисплее терминала URL  в виде QR-CODE
  *  @param[in] pQrCode URL Сбербанка должен начинаться с https://sberbank.ru/qr/.
  *  @param[out] нет.
  *  @return int Код ошибки.
 */
#ifdef PILOT_NT_DYNAMIC
typedef int (*fShowQrCodeDisplay)(char* pQrCode);
extern fShowQrCodeDisplay ShowQrCodeDisplay;
#else
PILOT_NT_API int ShowQrCodeDisplay(char* pQrCode);
#endif /*PILOT_NT_DYNAMIC*/
/**@}*/
#pragma pack()

#ifdef __cplusplus
};
#endif

#endif // _PILOT_NT_H_

