1/*
2 * Copyright (C) 2010 Apple Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 * 1. Redistributions of source code must retain the above copyright
8 *    notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 *    notice, this list of conditions and the following disclaimer in the
11 *    documentation and/or other materials provided with the distribution.
12 *
13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
14 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
15 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
17 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
18 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
19 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
20 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
21 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
22 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
23 * THE POSSIBILITY OF SUCH DAMAGE.
24 */
25
26#include "UserMessageCoders.h"
27#include "WebContext.h"
28#include "WebFrameProxy.h"
29#include "WebPageGroup.h"
30#include "WebPageGroupData.h"
31#include "WebPageProxy.h"
32
33#if PLATFORM(COCOA)
34#include "ObjCObjectGraphCoders.h"
35#endif
36
37namespace WebKit {
38
39// Adds
40// - Page -> BundlePage
41// - Frame -> BundleFrame
42// - PageGroup -> BundlePageGroup
43
44class WebContextUserMessageEncoder : public UserMessageEncoder<WebContextUserMessageEncoder> {
45public:
46    typedef UserMessageEncoder<WebContextUserMessageEncoder> Base;
47
48    explicit WebContextUserMessageEncoder(API::Object* root, WebProcessProxy& process)
49        : Base(root)
50        , m_process(process)
51    {
52    }
53
54    WebContextUserMessageEncoder(const WebContextUserMessageEncoder& userMessageEncoder, API::Object* root)
55        : Base(root)
56        , m_process(userMessageEncoder.m_process)
57    {
58    }
59
60    void encode(IPC::ArgumentEncoder& encoder) const
61    {
62        API::Object::Type type = API::Object::Type::Null;
63        if (baseEncode(encoder, *this, type))
64            return;
65
66        switch (type) {
67        case API::Object::Type::Page: {
68            WebPageProxy* page = static_cast<WebPageProxy*>(m_root);
69            encoder << page->pageID();
70            break;
71        }
72        case API::Object::Type::Frame: {
73            WebFrameProxy* frame = static_cast<WebFrameProxy*>(m_root);
74            encoder << frame->frameID();
75            break;
76        }
77        case API::Object::Type::PageGroup: {
78            WebPageGroup* pageGroup = static_cast<WebPageGroup*>(m_root);
79            encoder << pageGroup->data();
80            break;
81        }
82#if PLATFORM(COCOA)
83        case API::Object::Type::ObjCObjectGraph: {
84            ObjCObjectGraph* objectGraph = static_cast<ObjCObjectGraph*>(m_root);
85            encoder << WebContextObjCObjectGraphEncoder(objectGraph, m_process);
86            break;
87        }
88#endif
89        default:
90            ASSERT_NOT_REACHED();
91            break;
92        }
93    }
94
95private:
96    WebProcessProxy& m_process;
97};
98
99// Adds
100//   - Page -> BundlePage
101//   - Frame -> BundleFrame
102//   - PageGroup -> BundlePageGroup
103
104class WebContextUserMessageDecoder : public UserMessageDecoder<WebContextUserMessageDecoder> {
105public:
106    typedef UserMessageDecoder<WebContextUserMessageDecoder> Base;
107
108    WebContextUserMessageDecoder(RefPtr<API::Object>& root, WebProcessProxy& process)
109        : Base(root)
110        , m_process(process)
111    {
112    }
113
114    WebContextUserMessageDecoder(WebContextUserMessageDecoder& userMessageDecoder, RefPtr<API::Object>& root)
115        : Base(root)
116        , m_process(userMessageDecoder.m_process)
117    {
118    }
119
120    static bool decode(IPC::ArgumentDecoder& decoder, WebContextUserMessageDecoder& coder)
121    {
122        API::Object::Type type = API::Object::Type::Null;
123        if (!Base::baseDecode(decoder, coder, type))
124            return false;
125
126        if (coder.m_root || type == API::Object::Type::Null)
127            return true;
128
129        switch (type) {
130        case API::Object::Type::BundlePage: {
131            uint64_t pageID;
132            if (!decoder.decode(pageID))
133                return false;
134            coder.m_root = coder.m_process.webPage(pageID);
135            break;
136        }
137        case API::Object::Type::BundleFrame: {
138            uint64_t frameID;
139            if (!decoder.decode(frameID))
140                return false;
141            coder.m_root = coder.m_process.webFrame(frameID);
142            break;
143        }
144        case API::Object::Type::BundlePageGroup: {
145            uint64_t pageGroupID;
146            if (!decoder.decode(pageGroupID))
147                return false;
148            coder.m_root = WebPageGroup::get(pageGroupID);
149            break;
150        }
151#if PLATFORM(COCOA)
152        case API::Object::Type::ObjCObjectGraph: {
153            RefPtr<ObjCObjectGraph> objectGraph;
154            WebContextObjCObjectGraphDecoder objectGraphDecoder(objectGraph, coder.m_process);
155            if (!decoder.decode(objectGraphDecoder))
156                return false;
157            coder.m_root = objectGraph.get();
158            break;
159        }
160#endif
161        default:
162            return false;
163        }
164
165        return true;
166    }
167
168private:
169    WebProcessProxy& m_process;
170};
171
172} // namespace WebKit
173