ignite-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From sboi...@apache.org
Subject [38/50] [abbrv] ignite git commit: IGNITE-3390: Added DSN configuration window.
Date Thu, 08 Sep 2016 15:41:20 GMT
http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/custom_window.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/custom_window.h b/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/custom_window.h
new file mode 100644
index 0000000..1502c07
--- /dev/null
+++ b/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/custom_window.h
@@ -0,0 +1,189 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _IGNITE_ODBC_SYSTEM_UI_CUSTOM_WINDOW
+#define _IGNITE_ODBC_SYSTEM_UI_CUSTOM_WINDOW
+
+#include "ignite/odbc/system/ui/window.h"
+
+namespace ignite
+{
+    namespace odbc
+    {
+        namespace system
+        {
+            namespace ui
+            {
+                /**
+                 * Application execution result.
+                 */
+                enum Result
+                {
+                    RESULT_OK,
+                    RESULT_CANCEL
+                };
+
+                /**
+                 * Process UI messages in current thread.
+                 * Blocks until quit message has been received.
+                 *
+                 * @param window Main window.
+                 * @return Application execution result.
+                 */
+                Result ProcessMessages(Window& window);
+
+                /**
+                 * Window class.
+                 */
+                class CustomWindow : public Window
+                {
+                public:
+                    /**
+                     * Constructor.
+                     *
+                     * @param parent Parent window.
+                     * @param className Window class name.
+                     * @param title Window title.
+                     * @param callback Event processing function.
+                     */
+                    CustomWindow(Window* parent, const char* className, const char* title);
+
+                    /**
+                     * Destructor.
+                     */
+                    virtual ~CustomWindow();
+
+                    /**
+                     * Callback which is called upon receiving new message.
+                     * Pure virtual. Should be defined by user.
+                     *
+                     * @param msg Message.
+                     * @param wParam Word-sized parameter.
+                     * @param lParam Long parameter.
+                     * @return Should return true if the message has been
+                     *     processed by the handler and false otherwise.
+                     */
+                    virtual bool OnMessage(UINT msg, WPARAM wParam, LPARAM lParam) = 0;
+
+                    /**
+                     * Callback that is called upon window creation.
+                     */
+                    virtual void OnCreate() = 0;
+
+                    /**
+                     * Create child group box window.
+                     *
+                     * @param posX Position by X coordinate.
+                     * @param posY Position by Y coordinate.
+                     * @param sizeX Size by X coordinate.
+                     * @param sizeY Size by Y coordinate.
+                     * @param title Title.
+                     * @param id ID to be assigned to the created window.
+                     * @return Auto pointer containing new window.
+                     */
+                    std::auto_ptr<Window> CreateGroupBox(int posX, int posY,
+                        int sizeX, int sizeY, const char* title, int id);
+
+                    /**
+                     * Create child label window.
+                     *
+                     * @param posX Position by X coordinate.
+                     * @param posY Position by Y coordinate.
+                     * @param sizeX Size by X coordinate.
+                     * @param sizeY Size by Y coordinate.
+                     * @param title Title.
+                     * @param id ID to be assigned to the created window.
+                     * @return Auto pointer containing new window.
+                     */
+                    std::auto_ptr<Window> CreateLabel(int posX, int posY,
+                        int sizeX, int sizeY, const char* title, int id);
+
+                    /**
+                     * Create child Edit window.
+                     *
+                     * @param posX Position by X coordinate.
+                     * @param posY Position by Y coordinate.
+                     * @param sizeX Size by X coordinate.
+                     * @param sizeY Size by Y coordinate.
+                     * @param title Title.
+                     * @param id ID to be assigned to the created window.
+                     * @return Auto pointer containing new window.
+                     */
+                    std::auto_ptr<Window> CreateEdit(int posX, int posY,
+                        int sizeX, int sizeY, const char* title, int id, int style = 0);
+
+                    /**
+                     * Create child button window.
+                     *
+                     * @param posX Position by X coordinate.
+                     * @param posY Position by Y coordinate.
+                     * @param sizeX Size by X coordinate.
+                     * @param sizeY Size by Y coordinate.
+                     * @param title Title.
+                     * @param id ID to be assigned to the created window.
+                     * @return Auto pointer containing new window.
+                     */
+                    std::auto_ptr<Window> CreateButton(int posX, int posY,
+                        int sizeX, int sizeY, const char* title, int id);
+
+                    /**
+                     * Create child CheckBox window.
+                     *
+                     * @param posX Position by X coordinate.
+                     * @param posY Position by Y coordinate.
+                     * @param sizeX Size by X coordinate.
+                     * @param sizeY Size by Y coordinate.
+                     * @param title Title.
+                     * @param id ID to be assigned to the created window.
+                     * @return Auto pointer containing new window.
+                     */
+                    std::auto_ptr<Window> CreateCheckBox(int posX, int posY,
+                        int sizeX, int sizeY, const char* title, int id, bool state);
+
+                    /**
+                     * Create child ComboBox window.
+                     *
+                     * @param posX Position by X coordinate.
+                     * @param posY Position by Y coordinate.
+                     * @param sizeX Size by X coordinate.
+                     * @param sizeY Size by Y coordinate.
+                     * @param title Title.
+                     * @param id ID to be assigned to the created window.
+                     * @return Auto pointer containing new window.
+                     */
+                    std::auto_ptr<Window> CreateComboBox(int posX, int posY,
+                        int sizeX, int sizeY, const char* title, int id);
+                private:
+                    IGNITE_NO_COPY_ASSIGNMENT(CustomWindow)
+
+                    /**
+                     * Static callback.
+                     *
+                     * @param hwnd Window handle.
+                     * @param msg Message.
+                     * @param wParam Word-sized parameter.
+                     * @param lParam Long parameter.
+                     * @return Operation result.
+                     */
+                    static LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
+                };
+            }
+        }
+    }
+}
+
+#endif //_IGNITE_ODBC_SYSTEM_UI_CUSTOM_WINDOW
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/window.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/window.h b/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/window.h
new file mode 100644
index 0000000..32a54b2
--- /dev/null
+++ b/modules/platforms/cpp/odbc/os/win/include/ignite/odbc/system/ui/window.h
@@ -0,0 +1,201 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _IGNITE_ODBC_SYSTEM_UI_WINDOW
+#define _IGNITE_ODBC_SYSTEM_UI_WINDOW
+
+#include "ignite/odbc/utility.h"
+#include "ignite/odbc/system/odbc_constants.h"
+
+namespace ignite
+{
+    namespace odbc
+    {
+        namespace system
+        {
+            namespace ui
+            {
+                /**
+                 * Get handle for the current module.
+                 *
+                 * @return Handle for the current module.
+                 */
+                HINSTANCE GetHInstance();
+
+                /**
+                 * Window class.
+                 */
+                class Window
+                {
+                public:
+                    /**
+                     * Constructor for a new window that is going to be created.
+                     *
+                     * @param parent Parent window handle.
+                     * @param className Window class name.
+                     * @param title Window title.
+                     * @param callback Event processing function.
+                     */
+                    Window(Window* parent, const char* className, const char* title);
+
+                    /**
+                     * Constructor for the existing window.
+                     *
+                     * @param handle Window handle.
+                     */
+                    Window(HWND handle);
+
+                    /**
+                     * Destructor.
+                     */
+                    virtual ~Window();
+
+                    /**
+                     * Create window.
+                     *
+                     * @param style Window style.
+                     * @param posX Window x position.
+                     * @param posY Window y position.
+                     * @param width Window width.
+                     * @param height Window height.
+                     * @param id ID for child window.
+                     */
+                    void Create(DWORD style, int posX, int posY, int width, int height, int id);
+
+                    /**
+                     * Show window.
+                     */
+                    void Show();
+
+                    /**
+                     * Update window.
+                     */
+                    void Update();
+
+                    /**
+                     * Destroy window.
+                     */
+                    void Destroy();
+
+                    /**
+                     * Get window handle.
+                     *
+                     * @return Window handle.
+                     */
+                    HWND GetHandle() const
+                    {
+                        return handle;
+                    }
+
+                    /**
+                     * Get window text.
+                     *
+                     * @param text Text.
+                     */
+                    void GetText(std::string& text) const;
+
+                    /**
+                     * Set window text.
+                     *
+                     * @param text Text.
+                     */
+                    void SetText(const std::string& text) const;
+
+                    /**
+                     * Get CheckBox state.
+                     *
+                     * @param True if checked.
+                     */
+                    bool IsChecked() const;
+
+                    /**
+                     * Set CheckBox state.
+                     *
+                     * @param state True if checked.
+                     */
+                    void SetChecked(bool state);
+
+                    /**
+                     * Add string.
+                     *
+                     * @param str String.
+                     */
+                    void AddString(const std::string& str);
+
+                    /**
+                     * Set current ComboBox selection.
+                     *
+                     * @param idx List index.
+                     */
+                    void SetSelection(int idx);
+
+                    /**
+                     * Get current ComboBox selection.
+                     *
+                     * @return idx List index.
+                     */
+                    int GetSelection() const;
+
+                    /**
+                     * Set enabled.
+                     *
+                     * @param enabled Enable flag.
+                     */
+                    void SetEnabled(bool enabled);
+
+                    /**
+                     * Check if the window is enabled.
+                     *
+                     * @return True if enabled.
+                     */
+                    bool IsEnabled() const;
+
+                protected:
+                    /**
+                     * Set window handle.
+                     *
+                     * @param value Window handle.
+                     */
+                    void SetHandle(HWND value)
+                    {
+                        handle = value;
+                    }
+
+                    /** Window class name. */
+                    std::string className;
+
+                    /** Window title. */
+                    std::string title;
+
+                    /** Window handle. */
+                    HWND handle;
+
+                    /** Specifies whether window has been created by the thread and needs destruction. */
+                    bool created;
+
+                    /** Window parent. */
+                    Window* parent;
+
+                private:
+                    IGNITE_NO_COPY_ASSIGNMENT(Window)
+                };
+            }
+        }
+    }
+}
+
+#endif //_IGNITE_ODBC_SYSTEM_UI_WINDOW
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/os/win/src/system/ui/custom_window.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/os/win/src/system/ui/custom_window.cpp b/modules/platforms/cpp/odbc/os/win/src/system/ui/custom_window.cpp
new file mode 100644
index 0000000..1e855a1
--- /dev/null
+++ b/modules/platforms/cpp/odbc/os/win/src/system/ui/custom_window.cpp
@@ -0,0 +1,184 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <Windowsx.h>
+
+#include "ignite/odbc/system/ui/custom_window.h"
+
+namespace ignite
+{
+    namespace odbc
+    {
+        namespace system
+        {
+            namespace ui
+            {
+                Result ProcessMessages(Window& window)
+                {
+                    MSG msg;
+
+                    while (GetMessage(&msg, NULL, 0, 0) > 0)
+                    {
+                        if (!IsDialogMessage(window.GetHandle(), &msg))
+                        {
+                            TranslateMessage(&msg);
+
+                            DispatchMessage(&msg);
+                        }
+                    }
+
+                    return static_cast<Result>(msg.wParam);
+                }
+
+                LRESULT CALLBACK CustomWindow::WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+                {
+                    CustomWindow* window = reinterpret_cast<CustomWindow*>(GetWindowLongPtr(hwnd, GWLP_USERDATA));
+
+                    switch (msg)
+                    {
+                        case WM_NCCREATE:
+                        {
+                            _ASSERT(lParam != NULL);
+
+                            CREATESTRUCT* createStruct = reinterpret_cast<CREATESTRUCT*>(lParam);
+
+                            LONG_PTR longSelfPtr = reinterpret_cast<LONG_PTR>(createStruct->lpCreateParams);
+
+                            SetWindowLongPtr(hwnd, GWLP_USERDATA, longSelfPtr);
+
+                            return DefWindowProc(hwnd, msg, wParam, lParam);
+                        }
+
+                        case WM_CREATE:
+                        {
+                            _ASSERT(window != NULL);
+
+                            window->SetHandle(hwnd);
+
+                            window->OnCreate();
+
+                            return 0;
+                        }
+
+                        default:
+                            break;
+                    }
+
+                    if (window && window->OnMessage(msg, wParam, lParam))
+                        return 0;
+
+                    return DefWindowProc(hwnd, msg, wParam, lParam);
+                }
+
+                CustomWindow::CustomWindow(Window* parent, const char* className, const char* title) :
+                    Window(parent, className, title)
+                {
+                    WNDCLASS wcx;
+
+                    wcx.style = CS_HREDRAW | CS_VREDRAW;
+                    wcx.lpfnWndProc = WndProc;
+                    wcx.cbClsExtra = 0;
+                    wcx.cbWndExtra = 0;
+                    wcx.hInstance = GetHInstance();
+                    wcx.hIcon = NULL;
+                    wcx.hCursor = LoadCursor(NULL, IDC_ARROW);
+                    wcx.hbrBackground = (HBRUSH)COLOR_WINDOW;
+                    wcx.lpszMenuName = NULL;
+                    wcx.lpszClassName = className;
+
+
+                    if (!RegisterClass(&wcx))
+                    {
+                        std::stringstream buf;
+
+                        buf << "Can not register window class, error code: " << GetLastError();
+
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, buf.str().c_str());
+                    }
+                }
+
+                CustomWindow::~CustomWindow()
+                {
+                    UnregisterClass(className.c_str(), GetHInstance());
+                }
+
+                std::auto_ptr<Window> CustomWindow::CreateGroupBox(int posX, int posY,
+                    int sizeX, int sizeY, const char* title, int id)
+                {
+                    std::auto_ptr<Window> child(new Window(this, "Button", title));
+
+                    child->Create(WS_CHILD | WS_VISIBLE | BS_GROUPBOX, posX, posY, sizeX, sizeY, id);
+
+                    return child;
+                }
+
+                std::auto_ptr<Window> CustomWindow::CreateLabel(int posX, int posY,
+                    int sizeX, int sizeY, const char* title, int id)
+                {
+                    std::auto_ptr<Window> child(new Window(this, "Static", title));
+
+                    child->Create(WS_CHILD | WS_VISIBLE, posX, posY, sizeX, sizeY, id);
+
+                    return child;
+                }
+
+                std::auto_ptr<Window> CustomWindow::CreateEdit(int posX, int posY,
+                    int sizeX, int sizeY, const char* title, int id, int style)
+                {
+                    std::auto_ptr<Window> child(new Window(this, "Edit", title));
+
+                    child->Create(WS_CHILD | WS_VISIBLE | WS_BORDER | ES_AUTOHSCROLL | WS_TABSTOP | style,
+                        posX, posY, sizeX, sizeY, id);
+
+                    return child;
+                }
+
+                std::auto_ptr<Window> CustomWindow::CreateButton(int posX, int posY,
+                    int sizeX, int sizeY, const char* title, int id)
+                {
+                    std::auto_ptr<Window> child(new Window(this, "Button", title));
+
+                    child->Create(WS_CHILD | WS_VISIBLE | WS_TABSTOP, posX, posY, sizeX, sizeY, id);
+
+                    return child;
+                }
+
+                std::auto_ptr<Window> CustomWindow::CreateCheckBox(int posX, int posY,
+                    int sizeX, int sizeY, const char* title, int id, bool state)
+                {
+                    std::auto_ptr<Window> child(new Window(this, "Button", title));
+
+                    child->Create(WS_CHILD | WS_VISIBLE | BS_CHECKBOX, posX, posY, sizeX, sizeY, id);
+
+                    child->SetChecked(state);
+
+                    return child;
+                }
+
+                std::auto_ptr<Window> CustomWindow::CreateComboBox(int posX, int posY,
+                    int sizeX, int sizeY, const char * title, int id)
+                {
+                    std::auto_ptr<Window> child(new Window(this, "Combobox", title));
+
+                    child->Create(WS_CHILD | WS_VISIBLE | CBS_DROPDOWNLIST, posX, posY, sizeX, sizeY, id);
+
+                    return child;
+                }
+            }
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/os/win/src/system/ui/dsn_configuration_window.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/os/win/src/system/ui/dsn_configuration_window.cpp b/modules/platforms/cpp/odbc/os/win/src/system/ui/dsn_configuration_window.cpp
new file mode 100644
index 0000000..76132bd
--- /dev/null
+++ b/modules/platforms/cpp/odbc/os/win/src/system/ui/dsn_configuration_window.cpp
@@ -0,0 +1,212 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <Windowsx.h>
+
+#include "ignite/odbc/system/ui/dsn_configuration_window.h"
+
+namespace ignite
+{
+    namespace odbc
+    {
+        namespace system
+        {
+            namespace ui
+            {
+                DsnConfigurationWindow::DsnConfigurationWindow(Window* parent, config::Configuration& config):
+                    CustomWindow(parent, "IgniteConfigureDsn", "Configure Apache Ignite DSN"),
+                    width(360),
+                    height(160),
+                    connectionSettingsGroupBox(),
+                    nameLabel(),
+                    nameEdit(),
+                    addressLabel(),
+                    addressEdit(),
+                    cacheLabel(),
+                    cacheEdit(),
+                    okButton(),
+                    cancelButton(),
+                    config(config),
+                    accepted(false)
+                {
+                    // No-op.
+                }
+
+                DsnConfigurationWindow::~DsnConfigurationWindow()
+                {
+                    // No-op.
+                }
+
+                void DsnConfigurationWindow::Create()
+                {
+                    // Finding out parent position.
+                    RECT parentRect;
+                    GetWindowRect(parent->GetHandle(), &parentRect);
+
+                    // Positioning window to the center of parent window.
+                    const int posX = parentRect.left + (parentRect.right - parentRect.left - width) / 2;
+                    const int posY = parentRect.top + (parentRect.bottom - parentRect.top - height) / 2;
+
+                    RECT desiredRect = {posX, posY, posX + width, posY + height};
+                    AdjustWindowRect(&desiredRect, WS_BORDER | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME, FALSE);
+
+                    Window::Create(WS_OVERLAPPED | WS_SYSMENU, desiredRect.left, desiredRect.top,
+                        desiredRect.right - desiredRect.left, desiredRect.bottom - desiredRect.top, 0);
+
+                    if (!handle)
+                    {
+                        std::stringstream buf;
+
+                        buf << "Can not create window, error code: " << GetLastError();
+
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, buf.str().c_str());
+                    }
+                }
+
+                void DsnConfigurationWindow::OnCreate()
+                {
+                    int margin = 10;
+                    int interval = 10;
+
+                    int labelSizeX = 80;
+                    int labelPosX = margin + interval;
+
+                    int editSizeX = width - labelSizeX - 2 * margin - 3 * interval;
+                    int editPosX = margin + labelSizeX + 2 * interval;
+
+                    int rowSize = 20;
+                    int rowPos = margin + 2 * interval;
+
+                    int checkBoxSize = (editSizeX - interval) / 2;
+
+                    int sectionBegin = margin;
+
+                    const char* val = config.GetDsn().c_str();
+                    nameLabel = CreateLabel(labelPosX, rowPos, labelSizeX, rowSize, "DSN name:", ID_NAME_LABEL);
+                    nameEdit = CreateEdit(editPosX, rowPos, editSizeX, rowSize, val, ID_NAME_EDIT);
+
+                    rowPos += interval + rowSize;
+
+                    val = config.GetAddress().c_str();
+                    addressLabel = CreateLabel(labelPosX, rowPos, labelSizeX, rowSize, "Address:", ID_ADDRESS_LABEL);
+                    addressEdit = CreateEdit(editPosX, rowPos, editSizeX, rowSize, val, ID_ADDRESS_EDIT);
+
+                    rowPos += interval + rowSize;
+
+                    val = config.GetCache().c_str();
+                    cacheLabel = CreateLabel(labelPosX, rowPos, labelSizeX, rowSize, "Cache name:", ID_CACHE_LABEL);
+                    cacheEdit = CreateEdit(editPosX, rowPos, editSizeX, rowSize, val, ID_CACHE_EDIT);
+
+                    rowPos += interval * 2 + rowSize;
+
+                    connectionSettingsGroupBox = CreateGroupBox(margin, sectionBegin, width - 2 * margin,
+                        rowPos - interval - sectionBegin, "Connection settings", ID_CONNECTION_SETTINGS_GROUP_BOX);
+
+                    int buttonSizeX = 80;
+                    int cancelPosX = width - margin - buttonSizeX;
+                    int okPosX = cancelPosX - interval - buttonSizeX;
+
+                    rowSize = 25;
+
+                    okButton = CreateButton(okPosX, rowPos, buttonSizeX, rowSize, "Ok", ID_OK_BUTTON);
+                    cancelButton = CreateButton(cancelPosX, rowPos, buttonSizeX, rowSize, "Cancel", ID_CANCEL_BUTTON);
+                }
+
+                bool DsnConfigurationWindow::OnMessage(UINT msg, WPARAM wParam, LPARAM lParam)
+                {
+                    switch (msg)
+                    {
+                        case WM_COMMAND:
+                        {
+                            switch (LOWORD(wParam))
+                            {
+                                case ID_OK_BUTTON:
+                                {
+                                    try
+                                    {
+                                        RetrieveParameters(config);
+
+                                        accepted = true;
+
+                                        PostMessage(GetHandle(), WM_CLOSE, 0, 0);
+                                    }
+                                    catch (IgniteError& err)
+                                    {
+                                        MessageBox(NULL, err.GetText(), "Error!", MB_ICONEXCLAMATION | MB_OK);
+                                    }
+
+                                    break;
+                                }
+
+                                case IDCANCEL:
+                                case ID_CANCEL_BUTTON:
+                                {
+                                    PostMessage(GetHandle(), WM_CLOSE, 0, 0);
+
+                                    break;
+                                }
+
+                                default:
+                                    return false;
+                            }
+
+                            break;
+                        }
+
+                        case WM_DESTROY:
+                        {
+                            PostQuitMessage(accepted ? RESULT_OK : RESULT_CANCEL);
+
+                            break;
+                        }
+
+                        default:
+                            return false;
+                    }
+
+                    return true;
+                }
+
+                void DsnConfigurationWindow::RetrieveParameters(config::Configuration& cfg) const
+                {
+                    std::string dsn;
+                    std::string address;
+                    std::string cache;
+
+                    nameEdit->GetText(dsn);
+                    addressEdit->GetText(address);
+                    cacheEdit->GetText(cache);
+
+                    common::StripSurroundingWhitespaces(address);
+                    common::StripSurroundingWhitespaces(dsn);
+
+                    LOG_MSG("Retriving arguments:\n");
+                    LOG_MSG("DSN:                %s\n", dsn.c_str());
+                    LOG_MSG("Address:            %s\n", address.c_str());
+                    LOG_MSG("Cache:              %s\n", cache.c_str());
+
+                    if (dsn.empty())
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, "DSN name can not be empty.");
+
+                    cfg.SetDsn(dsn);
+                    cfg.SetAddress(address);
+                    cfg.SetCache(cache);
+                }
+            }
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/os/win/src/system/ui/window.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/os/win/src/system/ui/window.cpp b/modules/platforms/cpp/odbc/os/win/src/system/ui/window.cpp
new file mode 100644
index 0000000..1143f01
--- /dev/null
+++ b/modules/platforms/cpp/odbc/os/win/src/system/ui/window.cpp
@@ -0,0 +1,192 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <Windowsx.h>
+
+#include "ignite/odbc/system/ui/window.h"
+
+namespace ignite
+{
+    namespace odbc
+    {
+        namespace system
+        {
+            namespace ui
+            {
+                HINSTANCE GetHInstance()
+                {
+                    HINSTANCE hInstance = GetModuleHandle(TARGET_MODULE_FULL_NAME);
+
+                    if (hInstance == NULL)
+                    {
+                        std::stringstream buf;
+
+                        buf << "Can not get hInstance for the module, error code: " << GetLastError();
+
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, buf.str().c_str());
+                    }
+
+                    return hInstance;
+                }
+
+                Window::Window(Window* parent, const char* className, const char* title) :
+                    className(className),
+                    title(title),
+                    handle(NULL),
+                    created(false),
+                    parent(parent)
+                {
+                    // No-op.
+                }
+
+                Window::Window(HWND handle) :
+                    className(),
+                    title(),
+                    handle(handle),
+                    created(false),
+                    parent(0)
+                {
+                    // No-op.
+                }
+
+                Window::~Window()
+                {
+                    if (created)
+                        Destroy();
+                }
+
+                void Window::Create(DWORD style, int posX, int posY, int width, int height, int id)
+                {
+                    if (handle)
+                    {
+                        std::stringstream buf;
+
+                        buf << "Window already created, error code: " << GetLastError();
+
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, buf.str().c_str());
+                    }
+
+                    handle = CreateWindow(
+                        className.c_str(),
+                        title.c_str(),
+                        style,
+                        posX,
+                        posY,
+                        width,
+                        height,
+                        parent ? parent->GetHandle() : NULL,
+                        reinterpret_cast<HMENU>(id),
+                        GetHInstance(),
+                        this
+                    );
+
+                    if (!handle)
+                    {
+                        std::stringstream buf;
+
+                        buf << "Can not create window, error code: " << GetLastError();
+
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, buf.str().c_str());
+                    }
+
+                    created = true;
+
+                    HGDIOBJ hfDefault = GetStockObject(DEFAULT_GUI_FONT);
+
+                    SendMessage(GetHandle(), WM_SETFONT, (WPARAM)hfDefault, MAKELPARAM(FALSE, 0));
+                }
+
+                void Window::Show()
+                {
+                    ShowWindow(handle, SW_SHOW);
+                }
+
+                void Window::Update()
+                {
+                    UpdateWindow(handle);
+                }
+
+                void Window::Destroy()
+                {
+                    if (handle)
+                        DestroyWindow(handle);
+
+                    handle = NULL;
+                }
+
+                void Window::GetText(std::string& text) const
+                {
+                    int len = GetWindowTextLength(handle);
+
+                    if (len <= 0)
+                    {
+                        text.clear();
+
+                        return;
+                    }
+
+                    text.resize(len + 1);
+
+                    if (!GetWindowText(handle, &text[0], len + 1))
+                        text.clear();
+
+                    text.resize(len);
+                }
+
+                void Window::SetText(const std::string& text) const
+                {
+                    SNDMSG(handle, WM_SETTEXT, 0, reinterpret_cast<LPARAM>(text.c_str()));
+                }
+
+                bool Window::IsChecked() const
+                {
+                    return Button_GetCheck(handle) == BST_CHECKED;
+                }
+
+                void Window::SetChecked(bool state)
+                {
+                    Button_SetCheck(handle, state ? BST_CHECKED : BST_UNCHECKED);
+                }
+
+                void Window::AddString(const std::string & str)
+                {
+                    SNDMSG(handle, CB_ADDSTRING, 0, reinterpret_cast<LPARAM>(str.c_str()));
+                }
+
+                void Window::SetSelection(int idx)
+                {
+                    SNDMSG(handle, CB_SETCURSEL, static_cast<WPARAM>(idx), 0);
+                }
+
+                int Window::GetSelection() const
+                {
+                    return static_cast<int>(SNDMSG(handle, CB_GETCURSEL, 0, 0));
+                }
+
+                void Window::SetEnabled(bool enabled)
+                {
+                    EnableWindow(GetHandle(), enabled);
+                }
+
+                bool Window::IsEnabled() const
+                {
+                    return IsWindowEnabled(GetHandle()) != 0;
+                }
+            }
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/os/win/src/system_dsn.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/os/win/src/system_dsn.cpp b/modules/platforms/cpp/odbc/os/win/src/system_dsn.cpp
new file mode 100644
index 0000000..f432a40
--- /dev/null
+++ b/modules/platforms/cpp/odbc/os/win/src/system_dsn.cpp
@@ -0,0 +1,218 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "ignite/odbc/utility.h"
+#include "ignite/odbc/system/odbc_constants.h"
+
+#include "ignite/odbc/dsn_config.h"
+#include "ignite/odbc/system/ui/window.h"
+#include "ignite/odbc/system/ui/dsn_configuration_window.h"
+
+using ignite::odbc::config::Configuration;
+
+/**
+ * Display configuration window for user to configure DSN.
+ *
+ * @param hwndParent Parent window handle.
+ * @param config Output configuration.
+ * @return True on success and false on fail.
+ */
+bool DisplayConfigureDsnWindow(HWND hwndParent, Configuration& config)
+{
+    using namespace ignite::odbc::system::ui;
+
+    if (!hwndParent)
+        return false;
+
+    try
+    {
+        Window parent(hwndParent);
+
+        DsnConfigurationWindow window(&parent, config);
+
+        window.Create();
+
+        window.Show();
+        window.Update();
+
+        return ProcessMessages(window) == RESULT_OK;
+    }
+    catch (const ignite::IgniteError& err)
+    {
+        std::stringstream buf;
+
+        buf << "Message: " << err.GetText() << ", Code: " << err.GetCode();
+
+        std::string message = buf.str();
+
+        MessageBox(NULL, message.c_str(), "Error!", MB_ICONEXCLAMATION | MB_OK);
+
+        SQLPostInstallerError(err.GetCode(), err.GetText());
+    }
+
+    return false;
+}
+
+/**
+ * Register DSN with specified configuration.
+ *
+ * @param config Configuration.
+ * @param driver Driver.
+ * @return True on success and false on fail.
+ */
+bool RegisterDsn(const Configuration& config, LPCSTR driver)
+{
+    using namespace ignite::odbc::config;
+    using ignite::common::LexicalCast;
+
+    typedef Configuration::ArgumentMap ArgMap;
+
+    const char* dsn = config.GetDsn().c_str();
+
+    try
+    {
+        if (!SQLWriteDSNToIni(dsn, driver))
+            ignite::odbc::ThrowLastSetupError();
+
+        const ArgMap& map = config.GetMap();
+
+        std::set<std::string> ignore;
+
+        ignore.insert(Configuration::Key::dsn);
+        ignore.insert(Configuration::Key::driver);
+
+        for (ArgMap::const_iterator it = map.begin(); it != map.end(); ++it)
+        {
+            const std::string& key = it->first;
+            const std::string& value = it->second;
+
+            if (ignore.find(key) != ignore.end())
+                continue;
+
+            ignite::odbc::WriteDsnString(dsn, key.c_str(), value.c_str());
+        }
+
+        return true;
+    }
+    catch (ignite::IgniteError& err)
+    {
+        MessageBox(NULL, err.GetText(), "Error!", MB_ICONEXCLAMATION | MB_OK);
+
+        SQLPostInstallerError(err.GetCode(), err.GetText());
+    }
+
+    return false;
+}
+
+/**
+ * Unregister specified DSN.
+ *
+ * @param dsn DSN name.
+ * @return True on success and false on fail.
+ */
+bool UnregisterDsn(const char* dsn)
+{
+    try
+    {
+        if (!SQLRemoveDSNFromIni(dsn))
+            ignite::odbc::ThrowLastSetupError();
+
+        return true;
+    }
+    catch (ignite::IgniteError& err)
+    {
+        MessageBox(NULL, err.GetText(), "Error!", MB_ICONEXCLAMATION | MB_OK);
+
+        SQLPostInstallerError(err.GetCode(), err.GetText());
+    }
+
+    return false;
+}
+
+BOOL INSTAPI ConfigDSN(HWND hwndParent, WORD req, LPCSTR driver, LPCSTR attributes)
+{
+    using namespace ignite::odbc;
+
+    LOG_MSG("ConfigDSN called\n");
+
+    Configuration config;
+
+    LOG_MSG("Attributes: %s\n", attributes);
+
+    config.FillFromConfigAttributes(attributes);
+
+    if (!SQLValidDSN(config.GetDsn().c_str()))
+        return FALSE;
+
+    LOG_MSG("Driver: %s\n", driver);
+    LOG_MSG("Attributes: %s\n", attributes);
+
+    LOG_MSG("DSN: %s\n", config.GetDsn().c_str());
+
+    switch (req)
+    {
+        case ODBC_ADD_DSN:
+        {
+            LOG_MSG("ODBC_ADD_DSN\n");
+
+            if (!DisplayConfigureDsnWindow(hwndParent, config))
+                return FALSE;
+
+            if (!RegisterDsn(config, driver))
+                return FALSE;
+
+            break;
+        }
+
+        case ODBC_CONFIG_DSN:
+        {
+            LOG_MSG("ODBC_CONFIG_DSN\n");
+
+            std::string dsn = config.GetDsn();
+
+            Configuration loaded(config);
+
+            ReadDsnConfiguration(dsn.c_str(), loaded);
+
+            if (!DisplayConfigureDsnWindow(hwndParent, loaded))
+                return FALSE;
+
+            if (!RegisterDsn(loaded, driver))
+                return FALSE;
+
+            if (loaded.GetDsn() != dsn && !UnregisterDsn(dsn.c_str()))
+                return FALSE;
+
+            break;
+        }
+
+        case ODBC_REMOVE_DSN:
+        {
+            LOG_MSG("ODBC_REMOVE_DSN\n");
+
+            if (!UnregisterDsn(config.GetDsn().c_str()))
+                return FALSE;
+
+            break;
+        }
+
+        default:
+            return FALSE;
+    }
+
+    return TRUE;
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj b/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj
index 5820030..348a11a 100644
--- a/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj
+++ b/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj
@@ -93,8 +93,8 @@
       <WarningLevel>Level3</WarningLevel>
       <Optimization>Disabled</Optimization>
       <SDLCheck>false</SDLCheck>
-      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win\include;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;TARGET_MODULE_FULL_NAME="$(TargetFileName)";_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
     </ClCompile>
     <Link>
       <GenerateDebugInformation>true</GenerateDebugInformation>
@@ -107,8 +107,8 @@
       <WarningLevel>Level3</WarningLevel>
       <Optimization>Disabled</Optimization>
       <SDLCheck>false</SDLCheck>
-      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win\include;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;TARGET_MODULE_FULL_NAME="$(TargetFileName)";_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
     </ClCompile>
     <Link>
       <GenerateDebugInformation>true</GenerateDebugInformation>
@@ -123,8 +123,8 @@
       <FunctionLevelLinking>true</FunctionLevelLinking>
       <IntrinsicFunctions>true</IntrinsicFunctions>
       <SDLCheck>false</SDLCheck>
-      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win\include;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;TARGET_MODULE_FULL_NAME="$(TargetFileName)";%(PreprocessorDefinitions)</PreprocessorDefinitions>
     </ClCompile>
     <Link>
       <GenerateDebugInformation>true</GenerateDebugInformation>
@@ -141,8 +141,8 @@
       <FunctionLevelLinking>true</FunctionLevelLinking>
       <IntrinsicFunctions>true</IntrinsicFunctions>
       <SDLCheck>false</SDLCheck>
-      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>$(ProjectDir)\..\..\..\common\include;$(ProjectDir)\..\..\..\common\os\win\include;$(ProjectDir)\..\..\..\binary\include;$(ProjectDir)\..\..\..\binary\os\win\include;$(ProjectDir)\..\..\include;$(ProjectDir)\..\..\os\win\include;$(ProjectDir)\..\..\src</AdditionalIncludeDirectories>
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;IGNITE_IMPL;IGNITE_FRIEND;TARGET_MODULE_FULL_NAME="$(TargetFileName)";%(PreprocessorDefinitions)</PreprocessorDefinitions>
     </ClCompile>
     <Link>
       <GenerateDebugInformation>true</GenerateDebugInformation>
@@ -153,7 +153,11 @@
     </Link>
   </ItemDefinitionGroup>
   <ItemGroup>
+    <ClCompile Include="..\..\os\win\src\system_dsn.cpp" />
     <ClCompile Include="..\..\os\win\src\system\socket_client.cpp" />
+    <ClCompile Include="..\..\os\win\src\system\ui\custom_window.cpp" />
+    <ClCompile Include="..\..\os\win\src\system\ui\dsn_configuration_window.cpp" />
+    <ClCompile Include="..\..\os\win\src\system\ui\window.cpp" />
     <ClCompile Include="..\..\src\app\application_data_buffer.cpp" />
     <ClCompile Include="..\..\src\app\parameter.cpp" />
     <ClCompile Include="..\..\src\column.cpp" />
@@ -165,11 +169,13 @@
     <ClCompile Include="..\..\src\diagnostic\diagnosable_adapter.cpp" />
     <ClCompile Include="..\..\src\diagnostic\diagnostic_record.cpp" />
     <ClCompile Include="..\..\src\diagnostic\diagnostic_record_storage.cpp" />
+    <ClCompile Include="..\..\src\dsn_config.cpp" />
     <ClCompile Include="..\..\src\entry_points.cpp" />
     <ClCompile Include="..\..\src\environment.cpp" />
     <ClCompile Include="..\..\src\meta\column_meta.cpp" />
     <ClCompile Include="..\..\src\meta\table_meta.cpp" />
     <ClCompile Include="..\..\src\odbc.cpp" />
+    <ClCompile Include="..\..\src\protocol_version.cpp" />
     <ClCompile Include="..\..\src\query\data_query.cpp" />
     <ClCompile Include="..\..\src\query\column_metadata_query.cpp" />
     <ClCompile Include="..\..\src\query\foreign_keys_query.cpp" />
@@ -200,12 +206,14 @@
     <ClInclude Include="..\..\include\ignite\odbc\diagnostic\diagnosable_adapter.h" />
     <ClInclude Include="..\..\include\ignite\odbc\diagnostic\diagnostic_record.h" />
     <ClInclude Include="..\..\include\ignite\odbc\diagnostic\diagnostic_record_storage.h" />
+    <ClInclude Include="..\..\include\ignite\odbc\dsn_config.h" />
     <ClInclude Include="..\..\include\ignite\odbc\environment.h" />
     <ClInclude Include="..\..\include\ignite\odbc\message.h" />
     <ClInclude Include="..\..\include\ignite\odbc\meta\column_meta.h" />
     <ClInclude Include="..\..\include\ignite\odbc\meta\primary_key_meta.h" />
     <ClInclude Include="..\..\include\ignite\odbc\meta\table_meta.h" />
     <ClInclude Include="..\..\include\ignite\odbc\parser.h" />
+    <ClInclude Include="..\..\include\ignite\odbc\protocol_version.h" />
     <ClInclude Include="..\..\include\ignite\odbc\query\data_query.h" />
     <ClInclude Include="..\..\include\ignite\odbc\query\column_metadata_query.h" />
     <ClInclude Include="..\..\include\ignite\odbc\query\foreign_keys_query.h" />
@@ -219,8 +227,11 @@
     <ClInclude Include="..\..\include\ignite\odbc\statement.h" />
     <ClInclude Include="..\..\include\ignite\odbc\system\odbc_constants.h" />
     <ClInclude Include="..\..\include\ignite\odbc\system\socket_client.h" />
+    <ClInclude Include="..\..\include\ignite\odbc\system\ui\dsn_configuration_window.h" />
     <ClInclude Include="..\..\include\ignite\odbc\type_traits.h" />
     <ClInclude Include="..\..\include\ignite\odbc\utility.h" />
+    <ClInclude Include="..\..\os\win\include\ignite\odbc\system\ui\custom_window.h" />
+    <ClInclude Include="..\..\os\win\include\ignite\odbc\system\ui\window.h" />
   </ItemGroup>
   <ItemGroup>
     <ProjectReference Include="..\..\..\binary\project\vs\binary.vcxproj">

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj.filters
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj.filters b/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj.filters
index 6ca58e2..58764e4 100644
--- a/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj.filters
+++ b/modules/platforms/cpp/odbc/project/vs/odbc.vcxproj.filters
@@ -26,6 +26,9 @@
     <Filter Include="Code\diagnostic">
       <UniqueIdentifier>{df33e506-b5d8-423f-bcc5-1825242a3e28}</UniqueIdentifier>
     </Filter>
+    <Filter Include="Code\system\ui">
+      <UniqueIdentifier>{ff144e89-0a10-42c3-97dd-d22bfdbc7abb}</UniqueIdentifier>
+    </Filter>
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="..\..\src\odbc.cpp">
@@ -115,6 +118,24 @@
     <ClCompile Include="..\..\src\entry_points.cpp">
       <Filter>Code</Filter>
     </ClCompile>
+    <ClCompile Include="..\..\os\win\src\system\ui\window.cpp">
+      <Filter>Code\system\ui</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\os\win\src\system\ui\custom_window.cpp">
+      <Filter>Code\system\ui</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\os\win\src\system\ui\dsn_configuration_window.cpp">
+      <Filter>Code\system\ui</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\os\win\src\system_dsn.cpp">
+      <Filter>Code\system</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\src\dsn_config.cpp">
+      <Filter>Code</Filter>
+    </ClCompile>
+    <ClCompile Include="..\..\src\protocol_version.cpp">
+      <Filter>Code</Filter>
+    </ClCompile>
   </ItemGroup>
   <ItemGroup>
     <None Include="module.def">
@@ -224,5 +245,20 @@
     <ClInclude Include="..\..\include\ignite\odbc.h">
       <Filter>Code</Filter>
     </ClInclude>
+    <ClInclude Include="..\..\os\win\include\ignite\odbc\system\ui\window.h">
+      <Filter>Code\system\ui</Filter>
+    </ClInclude>
+    <ClInclude Include="..\..\os\win\include\ignite\odbc\system\ui\custom_window.h">
+      <Filter>Code\system\ui</Filter>
+    </ClInclude>
+    <ClInclude Include="..\..\include\ignite\odbc\system\ui\dsn_configuration_window.h">
+      <Filter>Code\system\ui</Filter>
+    </ClInclude>
+    <ClInclude Include="..\..\include\ignite\odbc\dsn_config.h">
+      <Filter>Code</Filter>
+    </ClInclude>
+    <ClInclude Include="..\..\include\ignite\odbc\protocol_version.h">
+      <Filter>Code</Filter>
+    </ClInclude>
   </ItemGroup>
 </Project>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/src/config/configuration.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/src/config/configuration.cpp b/modules/platforms/cpp/odbc/src/config/configuration.cpp
index 8d57dee..f40c74f 100644
--- a/modules/platforms/cpp/odbc/src/config/configuration.cpp
+++ b/modules/platforms/cpp/odbc/src/config/configuration.cpp
@@ -15,13 +15,14 @@
  * limitations under the License.
  */
 
-#include <cstring>
-
 #include <string>
 #include <sstream>
 #include <algorithm>
 #include <iterator>
 
+#include "ignite/common/common.h"
+#include "ignite/common/utils.h"
+
 #include "ignite/odbc/utility.h"
 #include "ignite/odbc/config/configuration.h"
 
@@ -31,50 +32,29 @@ namespace ignite
     {
         namespace config
         {
-            /** Default values for configuration. */
-            namespace dflt
-            {
-                /** Default value for DSN attribute. */
-                const std::string dsn = "Default Apache Ignite DSN";
+            const std::string Configuration::Key::dsn               = "dsn";
+            const std::string Configuration::Key::driver            = "driver";
+            const std::string Configuration::Key::cache             = "cache";
+            const std::string Configuration::Key::address           = "address";
+            const std::string Configuration::Key::server            = "server";
+            const std::string Configuration::Key::port              = "port";
+            const std::string Configuration::Key::protocolVersion   = "protocol_version";
 
-                /** Default value for Driver attribute. */
-                const std::string driver = "Apache Ignite";
+            const std::string Configuration::DefaultValue::dsn             = "Apache Ignite DSN";
+            const std::string Configuration::DefaultValue::driver          = "Apache Ignite";
+            const std::string Configuration::DefaultValue::cache           = "";
+            const std::string Configuration::DefaultValue::address         = "";
+            const std::string Configuration::DefaultValue::server          = "";
 
-                /** Default value for host attribute. */
-                const std::string host = "localhost";
+            const uint16_t Configuration::DefaultValue::port = 10800;
 
-                /** Default value for port attribute. */
-                const uint16_t port = 10800;
+            const ProtocolVersion& Configuration::DefaultValue::protocolVersion = ProtocolVersion::GetCurrent();
 
-                /** Default value for cache attribute. */
-                const std::string cache = "";
-            }
-
-            /** Connection attribute keywords. */
-            namespace attrkey
-            {
-                /** Connection attribute keyword for DSN attribute. */
-                const std::string dsn = "dsn";
-            
-                /** Connection attribute keyword for Driver attribute. */
-                const std::string driver = "driver";
-
-                /** Connection attribute keyword for server host attribute. */
-                const std::string host = "server";
-
-                /** Connection attribute keyword for server port attribute. */
-                const std::string port = "port";
-
-                /** Connection attribute keyword for cache attribute. */
-                const std::string cache = "cache";
-            }
 
             Configuration::Configuration() :
-                dsn(dflt::dsn), driver(dflt::driver),
-                host(dflt::host), port(dflt::port),
-                cache(dflt::cache)
+                arguments()
             {
-                // No-op.
+                ParseAddress(DefaultValue::address, endPoint);
             }
 
             Configuration::~Configuration()
@@ -84,7 +64,11 @@ namespace ignite
 
             void Configuration::FillFromConnectString(const char* str, size_t len)
             {
-                ArgumentMap connect_attributes;
+                // Initializing map.
+                arguments.clear();
+
+                // Initializing DSN to empty string.
+                arguments[Key::dsn].clear();
 
                 // Ignoring terminating zero byte if present.
                 // Some Driver Managers pass zero-terminated connection string
@@ -92,39 +76,19 @@ namespace ignite
                 if (len && !str[len - 1])
                     --len;
 
-                ParseAttributeList(str, len, ';', connect_attributes);
-
-                ArgumentMap::const_iterator it;
-
-                it = connect_attributes.find(attrkey::dsn);
-                if (it != connect_attributes.end())
-                    dsn = it->second;
-                else
-                    dsn.clear();
-
-                it = connect_attributes.find(attrkey::driver);
-                if (it != connect_attributes.end())
-                    driver = it->second;
-                else
-                    driver = dflt::driver;
-
-                it = connect_attributes.find(attrkey::host);
-                if (it != connect_attributes.end())
-                    host = it->second;
-                else
-                    host = dflt::host;
-
-                it = connect_attributes.find(attrkey::port);
-                if (it != connect_attributes.end())
-                    port = atoi(it->second.c_str());
-                else
-                    port = dflt::port;
+                ParseAttributeList(str, len, ';', arguments);
 
-                it = connect_attributes.find(attrkey::cache);
-                if (it != connect_attributes.end())
-                    cache = it->second;
+                ArgumentMap::const_iterator it = arguments.find(Key::address);
+                if (it != arguments.end())
+                {
+                    // Parsing address.
+                    ParseAddress(it->second, endPoint);
+                }
                 else
-                    cache = dflt::cache;
+                {
+                    endPoint.host = GetStringValue(Key::server, DefaultValue::server);
+                    endPoint.port = static_cast<uint16_t>(GetIntValue(Key::port, DefaultValue::port));
+                }
             }
 
             void Configuration::FillFromConnectString(const std::string& str)
@@ -136,27 +100,27 @@ namespace ignite
             {
                 std::stringstream connect_string_buffer;
 
-                if (!driver.empty())
-                    connect_string_buffer << attrkey::driver << "={" << driver << "};";
-
-                if (!host.empty())
-                    connect_string_buffer << attrkey::host << '=' << host << ';';
-
-                if (port)
-                    connect_string_buffer << attrkey::port << '=' << port << ';';
+                for (ArgumentMap::const_iterator it = arguments.begin(); it != arguments.end(); ++it)
+                {
+                    const std::string& key = it->first;
+                    const std::string& value = it->second;
 
-                if (!dsn.empty())
-                    connect_string_buffer << attrkey::dsn << '=' << dsn << ';';
+                    if (value.empty())
+                        continue;
 
-                if (!cache.empty())
-                    connect_string_buffer << attrkey::cache << '=' << cache << ';';
+                    if (value.find(' ') == std::string::npos)
+                        connect_string_buffer << key << '=' << value << ';';
+                    else
+                        connect_string_buffer << key << "={" << value << "};";
+                }
 
                 return connect_string_buffer.str();
             }
 
-            void Configuration::FillFromConfigAttributes(const char * attributes)
+            void Configuration::FillFromConfigAttributes(const char* attributes)
             {
-                ArgumentMap config_attributes;
+                // Initializing map.
+                arguments.clear();
 
                 size_t len = 0;
 
@@ -166,45 +130,74 @@ namespace ignite
 
                 ++len;
 
-                ParseAttributeList(attributes, len, '\0', config_attributes);
-
-                ArgumentMap::const_iterator it;
+                ParseAttributeList(attributes, len, '\0', arguments);
 
-                it = config_attributes.find(attrkey::dsn);
-                if (it != config_attributes.end())
-                    dsn = it->second;
+                ArgumentMap::const_iterator it = arguments.find(Key::address);
+                if (it != arguments.end())
+                {
+                    // Parsing address.
+                    ParseAddress(it->second, endPoint);
+                }
                 else
-                    dsn = dflt::dsn;
+                {
+                    endPoint.host = GetStringValue(Key::server, DefaultValue::server);
+                    endPoint.port = static_cast<uint16_t>(GetIntValue(Key::port, DefaultValue::port));
+                }
+            }
 
-                it = config_attributes.find(attrkey::driver);
-                if (it != config_attributes.end())
-                    driver = it->second;
-                else
-                    driver.clear();
+            void Configuration::SetTcpPort(uint16_t port)
+            {
+                arguments[Key::port] = common::LexicalCast<std::string>(port);
+            }
 
-                it = config_attributes.find(attrkey::host);
-                if (it != config_attributes.end())
-                    host = it->second;
-                else
-                    host.clear();
+            ProtocolVersion Configuration::GetProtocolVersion() const
+            {
+                ArgumentMap::const_iterator it = arguments.find(Key::protocolVersion);
 
-                it = config_attributes.find(attrkey::port);
-                if (it != config_attributes.end())
-                    port = atoi(it->second.c_str());
-                else
-                    port = 0;
+                if (it != arguments.end())
+                    return ProtocolVersion::FromString(it->second);
 
-                it = config_attributes.find(attrkey::cache);
-                if (it != config_attributes.end())
-                    cache = it->second;
-                else
-                    cache.clear();
+                return DefaultValue::protocolVersion;
+            }
+
+            void Configuration::SetProtocolVersion(const std::string& version)
+            {
+                arguments[Key::protocolVersion] = version;
+            }
+
+            const std::string& Configuration::GetStringValue(const std::string& key, const std::string& dflt) const
+            {
+                ArgumentMap::const_iterator it = arguments.find(common::ToLower(key));
+
+                if (it != arguments.end())
+                    return it->second;
+
+                return dflt;
             }
 
-            void Configuration::ParseAttributeList(const char * str, size_t len, char delimeter, ArgumentMap & args) const
+            int64_t Configuration::GetIntValue(const std::string& key, int64_t dflt) const
+            {
+                ArgumentMap::const_iterator it = arguments.find(common::ToLower(key));
+
+                if (it != arguments.end())
+                {
+                    const std::string& val = it->second;
+
+                    if (!common::AllOf(val.begin(), val.end(), isdigit))
+                        IGNITE_ERROR_FORMATTED_1(IgniteError::IGNITE_ERR_GENERIC,
+                            "Invalid argument value: Integer value is expected.", "key", key);
+
+                    return common::LexicalCast<int64_t>(val);
+                }
+
+                return dflt;
+            }
+
+
+
+            void Configuration::ParseAttributeList(const char * str, size_t len, char delimeter, ArgumentMap & args)
             {
                 std::string connect_str(str, len);
-                args.clear();
 
                 while (!connect_str.empty())
                 {
@@ -245,6 +238,51 @@ namespace ignite
                     connect_str.erase(attr_begin - 1);
                 }
             }
+
+            void Configuration::ParseAddress(const std::string& address, EndPoint& res)
+            {
+                int64_t colonNum = std::count(address.begin(), address.end(), ':');
+
+                if (colonNum == 0)
+                {
+                    res.host = address;
+                    res.port = DefaultValue::port;
+                }
+                else if (colonNum == 1)
+                {
+                    size_t pos = address.find(':');
+
+                    if (pos == address.size() - 1)
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC,
+                            "Invalid address format: no port after colon");
+
+                    res.host = address.substr(0, pos);
+
+                    std::string port = address.substr(pos + 1);
+
+                    if (!common::AllOf(port.begin(), port.end(), isdigit))
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC,
+                            "Invalid address format: port can only contain digits");
+
+                    int32_t intPort = common::LexicalCast<int32_t>(port);
+
+                    if (port.size() > sizeof("65535") - 1 || intPort > UINT16_MAX)
+                    {
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC,
+                            "Invalid address format: Port value is too large,"
+                            " valid value should be in range from 1 to 65535");
+                    }
+
+                    if (intPort == 0)
+                        throw IgniteError(IgniteError::IGNITE_ERR_GENERIC,
+                            "Invalid address format: Port value can not be zero");
+
+                    res.port = static_cast<uint16_t>(intPort);
+                }
+                else
+                    throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, 
+                        "Invalid address format: too many colons");
+            }
         }
     }
 }

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/src/connection.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/src/connection.cpp b/modules/platforms/cpp/odbc/src/connection.cpp
index 2441759..cffecdf 100644
--- a/modules/platforms/cpp/odbc/src/connection.cpp
+++ b/modules/platforms/cpp/odbc/src/connection.cpp
@@ -39,9 +39,11 @@ namespace ignite
 {
     namespace odbc
     {
-        const std::string Connection::PROTOCOL_VERSION_SINCE = "1.6.0";
-
-        Connection::Connection() : socket(), connected(false), cache(), parser()
+        Connection::Connection() :
+            socket(),
+            connected(false),
+            parser(),
+            config()
         {
             // No-op.
         }
@@ -53,8 +55,8 @@ namespace ignite
         
         const config::ConnectionInfo& Connection::GetInfo() const
         {
-            // Connection info is the same for all connections now.
-            static config::ConnectionInfo info;
+            // Connection info is constant and the same for all connections now.
+            const static config::ConnectionInfo info;
 
             return info;
         }
@@ -76,32 +78,38 @@ namespace ignite
             return res;
         }
 
-        void Connection::Establish(const std::string& server)
+        void Connection::Establish(const std::string& connectStr)
         {
-            IGNITE_ODBC_API_CALL(InternalEstablish(server));
+            IGNITE_ODBC_API_CALL(InternalEstablish(connectStr));
         }
 
-        SqlResult Connection::InternalEstablish(const std::string& server)
+        SqlResult Connection::InternalEstablish(const std::string& connectStr)
         {
             config::Configuration config;
 
-            if (server != config.GetDsn())
+            try
             {
-                AddStatusRecord(SQL_STATE_HY000_GENERAL_ERROR, "Unknown server.");
+                config.FillFromConnectString(connectStr);
+            }
+            catch (IgniteError& e)
+            {
+                AddStatusRecord(SQL_STATE_HY000_GENERAL_ERROR, e.GetText());
 
                 return SQL_RESULT_ERROR;
             }
 
-            return InternalEstablish(config.GetHost(), config.GetPort(), config.GetCache());
+            return InternalEstablish(config);
         }
 
-        void Connection::Establish(const std::string& host, uint16_t port, const std::string& cache)
+        void Connection::Establish(const config::Configuration cfg)
         {
-            IGNITE_ODBC_API_CALL(InternalEstablish(host, port, cache));
+            IGNITE_ODBC_API_CALL(InternalEstablish(cfg));
         }
 
-        SqlResult Connection::InternalEstablish(const std::string & host, uint16_t port, const std::string & cache)
+        SqlResult Connection::InternalEstablish(const config::Configuration cfg)
         {
+            config = cfg;
+
             if (connected)
             {
                 AddStatusRecord(SQL_STATE_08002_ALREADY_CONNECTED, "Already connected.");
@@ -109,9 +117,7 @@ namespace ignite
                 return SQL_RESULT_ERROR;
             }
 
-            this->cache = cache;
-
-            connected = socket.Connect(host.c_str(), port);
+            connected = socket.Connect(cfg.GetHost().c_str(), cfg.GetTcpPort());
 
             if (!connected)
             {
@@ -262,11 +268,16 @@ namespace ignite
 
         const std::string& Connection::GetCache() const
         {
-            return cache;
+            return config.GetCache();
+        }
+
+        const config::Configuration& Connection::GetConfiguration() const
+        {
+            return config;
         }
 
         diagnostic::DiagnosticRecord Connection::CreateStatusRecord(SqlState sqlState,
-            const std::string& message, int32_t rowNum, int32_t columnNum) const
+            const std::string& message, int32_t rowNum, int32_t columnNum)
         {
             return diagnostic::DiagnosticRecord(sqlState, message, "", "", rowNum, columnNum);
         }
@@ -296,7 +307,20 @@ namespace ignite
 
         SqlResult Connection::MakeRequestHandshake()
         {
-            HandshakeRequest req(PROTOCOL_VERSION);
+            int64_t protocolVersion = 0;
+
+            try
+            {
+                protocolVersion = config.GetProtocolVersion().GetIntValue();
+            }
+            catch (const IgniteError& err)
+            {
+                AddStatusRecord(SQL_STATE_01S00_INVALID_CONNECTION_STRING_ATTRIBUTE, err.GetText());
+
+                return SQL_RESULT_ERROR;
+            }
+
+            HandshakeRequest req(protocolVersion);
             HandshakeResponse rsp;
 
             try
@@ -330,7 +354,7 @@ namespace ignite
                 constructor << "Node rejected handshake message. "
                     << "Current node Apache Ignite version: " << rsp.CurrentVer() << ", "
                     << "node protocol version introduced in version: " << rsp.ProtoVerSince() << ", "
-                    << "driver protocol version introduced in version: " << PROTOCOL_VERSION_SINCE << ".";
+                    << "driver protocol version introduced in version: " << config.GetProtocolVersion().ToString() << ".";
 
                 AddStatusRecord(SQL_STATE_08001_CANNOT_CONNECT, constructor.str());
 

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record.cpp b/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record.cpp
index 568c125..8553ee4 100644
--- a/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record.cpp
+++ b/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record.cpp
@@ -34,6 +34,9 @@ namespace
     /** SQL state 01004 constant. */
     const std::string STATE_01004 = "01004";
 
+    /** SQL state 01S00 constant. */
+    const std::string STATE_01S00 = "01S00";
+
     /** SQL state 01S01 constant. */
     const std::string STATE_01S01 = "01S01";
 
@@ -168,7 +171,7 @@ namespace ignite
                 return ORIGIN_ISO_9075;
             }
 
-            const std::string& DiagnosticRecord::GetMessage() const
+            const std::string& DiagnosticRecord::GetMessageText() const
             {
                 return message;
             }
@@ -190,6 +193,9 @@ namespace ignite
                     case SQL_STATE_01004_DATA_TRUNCATED:
                         return STATE_01004;
 
+                    case SQL_STATE_01S00_INVALID_CONNECTION_STRING_ATTRIBUTE:
+                        return STATE_01S00;
+
                     case SQL_STATE_01S01_ERROR_IN_ROW:
                         return STATE_01S01;
 

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record_storage.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record_storage.cpp b/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record_storage.cpp
index 90c0a4f..99ef292 100644
--- a/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record_storage.cpp
+++ b/modules/platforms/cpp/odbc/src/diagnostic/diagnostic_record_storage.cpp
@@ -190,7 +190,7 @@ namespace ignite
 
                     case IGNITE_SQL_DIAG_STATUS_MESSAGE_TEXT:
                     {
-                        buffer.PutString(record.GetMessage());
+                        buffer.PutString(record.GetMessageText());
 
                         return SQL_RESULT_SUCCESS;
                     }

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/src/dsn_config.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/src/dsn_config.cpp b/modules/platforms/cpp/odbc/src/dsn_config.cpp
new file mode 100644
index 0000000..99635dc
--- /dev/null
+++ b/modules/platforms/cpp/odbc/src/dsn_config.cpp
@@ -0,0 +1,111 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <set>
+
+#include "ignite/odbc/utility.h"
+#include "ignite/odbc/system/odbc_constants.h"
+
+#include "ignite/odbc/dsn_config.h"
+
+using ignite::odbc::config::Configuration;
+
+#define BUFFER_SIZE 1024
+#define CONFIG_FILE "ODBC.INI"
+
+namespace ignite
+{
+    namespace odbc
+    {
+        void ThrowLastSetupError()
+        {
+            DWORD code;
+            char msg[BUFFER_SIZE];
+
+            SQLInstallerError(1, &code, msg, sizeof(msg), NULL);
+
+            std::stringstream buf;
+
+            buf << "Message: \"" << msg << "\", Code: " << code;
+
+            throw IgniteError(IgniteError::IGNITE_ERR_GENERIC, buf.str().c_str());
+        }
+
+        void WriteDsnString(const char* dsn, const char* key, const char* value)
+        {
+            if (!SQLWritePrivateProfileString(dsn, key, value, CONFIG_FILE))
+                ThrowLastSetupError();
+        }
+
+        std::string ReadDsnString(const char* dsn, const std::string& key, const char* dflt)
+        {
+            char buf[BUFFER_SIZE];
+
+            memset(buf, 0, sizeof(buf));
+
+            SQLGetPrivateProfileString(dsn, key.c_str(), dflt, buf, sizeof(buf), CONFIG_FILE);
+
+            return std::string(buf);
+        }
+
+        int ReadDsnInt(const char* dsn, const std::string& key, int dflt)
+        {
+            char buf[BUFFER_SIZE];
+
+            memset(buf, 0, sizeof(buf));
+
+            std::string dflt0 = common::LexicalCast<std::string>(dflt);
+
+            SQLGetPrivateProfileString(dsn, key.c_str(), dflt0.c_str(), buf, sizeof(buf), CONFIG_FILE);
+
+            return common::LexicalCast<int, std::string>(buf);
+        }
+
+        bool ReadDsnBool(const char* dsn, const std::string& key, bool dflt)
+        {
+            char buf[BUFFER_SIZE];
+
+            memset(buf, 0, sizeof(buf));
+
+            std::string dflt0 = dflt ? "true" : "false";
+
+            SQLGetPrivateProfileString(dsn, key.c_str(), dflt0.c_str(), buf, sizeof(buf), CONFIG_FILE);
+
+            return std::string(buf) == "true";
+        }
+
+        void ReadDsnConfiguration(const char* dsn, Configuration& config)
+        {
+            std::string address = ReadDsnString(dsn, Configuration::Key::address, config.GetAddress().c_str());
+            std::string server = ReadDsnString(dsn, Configuration::Key::server, config.GetHost().c_str());
+            uint16_t port = ReadDsnInt(dsn, Configuration::Key::port, config.GetTcpPort());
+            std::string cache = ReadDsnString(dsn, Configuration::Key::cache, config.GetCache().c_str());
+            std::string version = ReadDsnString(dsn, Configuration::Key::protocolVersion,
+                config.GetProtocolVersion().ToString().c_str());
+
+            LOG_MSG("%d\n", __LINE__);
+
+            config.SetAddress(address);
+            config.SetHost(server);
+            config.SetTcpPort(port);
+            config.SetCache(cache);
+            config.SetProtocolVersion(version);
+
+            LOG_MSG("%d\n", __LINE__);
+        }
+    }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/src/entry_points.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/src/entry_points.cpp b/modules/platforms/cpp/odbc/src/entry_points.cpp
index c8e78a5..f6195e1 100644
--- a/modules/platforms/cpp/odbc/src/entry_points.cpp
+++ b/modules/platforms/cpp/odbc/src/entry_points.cpp
@@ -19,14 +19,6 @@
 
 #include "ignite/odbc/utility.h"
 
-BOOL INSTAPI ConfigDSN(HWND     hwndParent,
-                       WORD     req,
-                       LPCSTR   driver,
-                       LPCSTR   attributes)
-{
-    return ignite::ConfigDSN(hwndParent, req, driver, attributes);
-}
-
 SQLRETURN SQL_API SQLGetInfo(SQLHDBC        conn,
                              SQLUSMALLINT   infoType,
                              SQLPOINTER     infoValue,

http://git-wip-us.apache.org/repos/asf/ignite/blob/70e69cb7/modules/platforms/cpp/odbc/src/odbc.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/odbc/src/odbc.cpp b/modules/platforms/cpp/odbc/src/odbc.cpp
index 3b31f1d..fd35cba 100644
--- a/modules/platforms/cpp/odbc/src/odbc.cpp
+++ b/modules/platforms/cpp/odbc/src/odbc.cpp
@@ -28,61 +28,11 @@
 #include "ignite/odbc/environment.h"
 #include "ignite/odbc/connection.h"
 #include "ignite/odbc/statement.h"
+#include "ignite/odbc/dsn_config.h"
 #include "ignite/odbc.h"
 
 namespace ignite
 {
-
-    BOOL ConfigDSN(HWND     hwndParent,
-                   WORD     req,
-                   LPCSTR   driver,
-                   LPCSTR   attributes)
-    {
-        LOG_MSG("ConfigDSN called\n");
-
-        ignite::odbc::config::Configuration config;
-
-        config.FillFromConfigAttributes(attributes);
-
-        if (!SQLValidDSN(config.GetDsn().c_str()))
-            return SQL_FALSE;
-
-        LOG_MSG("Driver: %s\n", driver);
-        LOG_MSG("Attributes: %s\n", attributes);
-
-        LOG_MSG("DSN: %s\n", config.GetDsn().c_str());
-
-        switch (req)
-        {
-            case ODBC_ADD_DSN:
-            {
-                LOG_MSG("ODBC_ADD_DSN\n");
-
-                return SQLWriteDSNToIni(config.GetDsn().c_str(), driver);
-            }
-
-            case ODBC_CONFIG_DSN:
-            {
-                LOG_MSG("ODBC_CONFIG_DSN\n");
-                break;
-            }
-
-            case ODBC_REMOVE_DSN:
-            {
-                LOG_MSG("ODBC_REMOVE_DSN\n");
-
-                return SQLRemoveDSNFromIni(config.GetDsn().c_str());
-            }
-
-            default:
-            {
-                return SQL_FALSE;
-            }
-        }
-
-        return SQL_TRUE;
-    }
-
     SQLRETURN SQLGetInfo(SQLHDBC        conn,
                          SQLUSMALLINT   infoType,
                          SQLPOINTER     infoValue,
@@ -306,10 +256,10 @@ namespace ignite
                                SQLSMALLINT* outConnectionStringLen,
                                SQLUSMALLINT driverCompletion)
     {
-        using ignite::odbc::Connection;
-        using ignite::odbc::diagnostic::DiagnosticRecordStorage;
-        using ignite::utility::SqlStringToString;
-        using ignite::utility::CopyStringToBuffer;
+        using odbc::Connection;
+        using odbc::diagnostic::DiagnosticRecordStorage;
+        using utility::SqlStringToString;
+        using utility::CopyStringToBuffer;
 
         UNREFERENCED_PARAMETER(windowHandle);
 
@@ -323,18 +273,23 @@ namespace ignite
 
         std::string connectStr = SqlStringToString(inConnectionString, inConnectionStringLen);
 
-        ignite::odbc::config::Configuration config;
+        odbc::config::Configuration config;
 
         config.FillFromConnectString(connectStr);
 
-        connection->Establish(config.GetHost(), config.GetPort(), config.GetCache());
+        std::string dsn = config.GetDsn();
+
+        if (!dsn.empty())
+            odbc::ReadDsnConfiguration(dsn.c_str(), config);
+
+        connection->Establish(config);
 
         const DiagnosticRecordStorage& diag = connection->GetDiagnosticRecords();
 
         if (!diag.IsSuccessful())
             return diag.GetReturnCode();
 
-        std::string outConnectStr = config.ToConnectString();
+        std::string outConnectStr = connection->GetConfiguration().ToConnectString();
 
         size_t reslen = CopyStringToBuffer(outConnectStr,
             reinterpret_cast<char*>(outConnectionString),
@@ -357,7 +312,7 @@ namespace ignite
                          SQLSMALLINT    authLen)
     {
         using ignite::odbc::Connection;
-        using ignite::odbc::diagnostic::DiagnosticRecordStorage;
+        using ignite::odbc::config::Configuration;
         using ignite::utility::SqlStringToString;
 
         LOG_MSG("SQLConnect called\n");
@@ -367,9 +322,13 @@ namespace ignite
         if (!connection)
             return SQL_INVALID_HANDLE;
 
-        std::string server = SqlStringToString(serverName, serverNameLen);
+        odbc::config::Configuration config;
+
+        std::string dsn = SqlStringToString(serverName, serverNameLen);
+
+        odbc::ReadDsnConfiguration(dsn.c_str(), config);
 
-        connection->Establish(server);
+        connection->Establish(config);
 
         return connection->GetDiagnosticRecords().GetReturnCode();
     }
@@ -1168,7 +1127,7 @@ namespace ignite
         SqlLen outResLen;
         ApplicationDataBuffer outBuffer(IGNITE_ODBC_C_TYPE_CHAR, msgBuffer, msgBufferLen, &outResLen);
 
-        outBuffer.PutString(record.GetMessage());
+        outBuffer.PutString(record.GetMessageText());
 
         *msgLen = static_cast<SQLSMALLINT>(outResLen);
 


Mime
View raw message