graph_apis.cc 12.5 KB
Newer Older
Minjie Wang's avatar
Minjie Wang committed
1
#include <dgl/graph.h>
Minjie Wang's avatar
Minjie Wang committed
2
#include <dgl/graph_op.h>
Lingfan Yu's avatar
Lingfan Yu committed
3
#include "../c_api_common.h"
Minjie Wang's avatar
Minjie Wang committed
4
5
6
7
8

using tvm::runtime::TVMArgs;
using tvm::runtime::TVMArgValue;
using tvm::runtime::TVMRetValue;
using tvm::runtime::PackedFunc;
Minjie Wang's avatar
Minjie Wang committed
9
using tvm::runtime::NDArray;
Minjie Wang's avatar
Minjie Wang committed
10
11

namespace dgl {
Minjie Wang's avatar
Minjie Wang committed
12

Minjie Wang's avatar
Minjie Wang committed
13
namespace {
Minjie Wang's avatar
Minjie Wang committed
14
// Convert EdgeArray structure to PackedFunc.
15
16
PackedFunc ConvertEdgeArrayToPackedFunc(const Graph::EdgeArray& ea) {
  auto body = [ea] (TVMArgs args, TVMRetValue* rv) {
Minjie Wang's avatar
Minjie Wang committed
17
      int which = args[0];
18
      if (which == 0) {
Minjie Wang's avatar
Minjie Wang committed
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
        *rv = std::move(ea.src);
      } else if (which == 1) {
        *rv = std::move(ea.dst);
      } else if (which == 2) {
        *rv = std::move(ea.id);
      } else {
        LOG(FATAL) << "invalid choice";
      }
    };
  return PackedFunc(body);
}

// Convert Subgraph structure to PackedFunc.
PackedFunc ConvertSubgraphToPackedFunc(const Subgraph& sg) {
  auto body = [sg] (TVMArgs args, TVMRetValue* rv) {
      int which = args[0];
      if (which == 0) {
        Graph* gptr = new Graph();
        *gptr = std::move(sg.graph);
        GraphHandle ghandle = gptr;
        *rv = ghandle;
40
      } else if (which == 1) {
Minjie Wang's avatar
Minjie Wang committed
41
        *rv = std::move(sg.induced_vertices);
42
      } else if (which == 2) {
Minjie Wang's avatar
Minjie Wang committed
43
        *rv = std::move(sg.induced_edges);
44
45
46
      } else {
        LOG(FATAL) << "invalid choice";
      }
Minjie Wang's avatar
Minjie Wang committed
47
48
49
    };
  return PackedFunc(body);
}
Minjie Wang's avatar
Minjie Wang committed
50

Minjie Wang's avatar
Minjie Wang committed
51
}  // namespace
Minjie Wang's avatar
Minjie Wang committed
52

Minjie Wang's avatar
Minjie Wang committed
53
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphCreate")
Minjie Wang's avatar
Minjie Wang committed
54
.set_body([] (TVMArgs args, TVMRetValue* rv) {
55
56
    bool multigraph = static_cast<bool>(args[0]);
    GraphHandle ghandle = new Graph(multigraph);
Minjie Wang's avatar
Minjie Wang committed
57
58
    *rv = ghandle;
  });
Minjie Wang's avatar
Minjie Wang committed
59

Minjie Wang's avatar
Minjie Wang committed
60
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphFree")
Minjie Wang's avatar
Minjie Wang committed
61
62
63
64
65
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    Graph* gptr = static_cast<Graph*>(ghandle);
    delete gptr;
  });
Minjie Wang's avatar
Minjie Wang committed
66

Minjie Wang's avatar
Minjie Wang committed
67
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphAddVertices")
Minjie Wang's avatar
Minjie Wang committed
68
69
70
71
72
73
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    Graph* gptr = static_cast<Graph*>(ghandle);
    uint64_t num_vertices = args[1];
    gptr->AddVertices(num_vertices);
  });
Minjie Wang's avatar
Minjie Wang committed
74

Minjie Wang's avatar
Minjie Wang committed
75
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphAddEdge")
Minjie Wang's avatar
Minjie Wang committed
76
77
78
79
80
81
82
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t src = args[1];
    const dgl_id_t dst = args[2];
    gptr->AddEdge(src, dst);
  });
Minjie Wang's avatar
Minjie Wang committed
83

Minjie Wang's avatar
Minjie Wang committed
84
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphAddEdges")
Minjie Wang's avatar
Minjie Wang committed
85
86
87
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
88
89
    const IdArray src = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
    const IdArray dst = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[2]));
Minjie Wang's avatar
Minjie Wang committed
90
91
92
    gptr->AddEdges(src, dst);
  });

Minjie Wang's avatar
Minjie Wang committed
93
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphClear")
Minjie Wang's avatar
Minjie Wang committed
94
95
96
97
98
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    Graph* gptr = static_cast<Graph*>(ghandle);
    gptr->Clear();
  });
Minjie Wang's avatar
Minjie Wang committed
99

100
101
102
103
104
105
106
107
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphIsMultigraph")
.set_body([] (TVMArgs args, TVMRetValue *rv) {
    GraphHandle ghandle = args[0];
    // NOTE: not const since we have caches
    const Graph* gptr = static_cast<Graph*>(ghandle);
    *rv = gptr->IsMultigraph();
  });

Minjie Wang's avatar
Minjie Wang committed
108
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphNumVertices")
Minjie Wang's avatar
Minjie Wang committed
109
110
111
112
113
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    *rv = static_cast<int64_t>(gptr->NumVertices());
  });
Minjie Wang's avatar
Minjie Wang committed
114

Minjie Wang's avatar
Minjie Wang committed
115
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphNumEdges")
Minjie Wang's avatar
Minjie Wang committed
116
117
118
119
120
121
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    *rv = static_cast<int64_t>(gptr->NumEdges());
  });

Minjie Wang's avatar
Minjie Wang committed
122
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphHasVertex")
Minjie Wang's avatar
Minjie Wang committed
123
124
125
126
127
128
129
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t vid = args[1];
    *rv = gptr->HasVertex(vid);
  });

Minjie Wang's avatar
Minjie Wang committed
130
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphHasVertices")
Minjie Wang's avatar
Minjie Wang committed
131
132
133
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
134
    const IdArray vids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
Minjie Wang's avatar
Minjie Wang committed
135
136
137
    *rv = gptr->HasVertices(vids);
  });

138
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphHasEdgeBetween")
Minjie Wang's avatar
Minjie Wang committed
139
140
141
142
143
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t src = args[1];
    const dgl_id_t dst = args[2];
144
    *rv = gptr->HasEdgeBetween(src, dst);
Minjie Wang's avatar
Minjie Wang committed
145
146
  });

147
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphHasEdgesBetween")
Minjie Wang's avatar
Minjie Wang committed
148
149
150
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
151
152
    const IdArray src = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
    const IdArray dst = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[2]));
153
    *rv = gptr->HasEdgesBetween(src, dst);
Minjie Wang's avatar
Minjie Wang committed
154
155
  });

Minjie Wang's avatar
Minjie Wang committed
156
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphPredecessors")
Minjie Wang's avatar
Minjie Wang committed
157
158
159
160
161
162
163
164
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t vid = args[1];
    const uint64_t radius = args[2];
    *rv = gptr->Predecessors(vid, radius);
  });

Minjie Wang's avatar
Minjie Wang committed
165
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphSuccessors")
Minjie Wang's avatar
Minjie Wang committed
166
167
168
169
170
171
172
173
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t vid = args[1];
    const uint64_t radius = args[2];
    *rv = gptr->Successors(vid, radius);
  });

Minjie Wang's avatar
Minjie Wang committed
174
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphEdgeId")
Minjie Wang's avatar
Minjie Wang committed
175
176
177
178
179
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t src = args[1];
    const dgl_id_t dst = args[2];
180
    *rv = gptr->EdgeId(src, dst);
Minjie Wang's avatar
Minjie Wang committed
181
182
  });

Minjie Wang's avatar
Minjie Wang committed
183
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphEdgeIds")
Minjie Wang's avatar
Minjie Wang committed
184
185
186
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
187
188
    const IdArray src = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
    const IdArray dst = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[2]));
189
190
191
192
193
194
195
196
197
    *rv = ConvertEdgeArrayToPackedFunc(gptr->EdgeIds(src, dst));
  });

TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphFindEdges")
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const IdArray eids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
    *rv = ConvertEdgeArrayToPackedFunc(gptr->FindEdges(eids));
Minjie Wang's avatar
Minjie Wang committed
198
199
  });

Minjie Wang's avatar
Minjie Wang committed
200
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphInEdges_1")
Minjie Wang's avatar
Minjie Wang committed
201
202
203
204
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t vid = args[1];
205
    *rv = ConvertEdgeArrayToPackedFunc(gptr->InEdges(vid));
Minjie Wang's avatar
Minjie Wang committed
206
207
  });

Minjie Wang's avatar
Minjie Wang committed
208
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphInEdges_2")
Minjie Wang's avatar
Minjie Wang committed
209
210
211
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
212
    const IdArray vids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
213
    *rv = ConvertEdgeArrayToPackedFunc(gptr->InEdges(vids));
Minjie Wang's avatar
Minjie Wang committed
214
215
  });

Minjie Wang's avatar
Minjie Wang committed
216
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphOutEdges_1")
Minjie Wang's avatar
Minjie Wang committed
217
218
219
220
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t vid = args[1];
221
    *rv = ConvertEdgeArrayToPackedFunc(gptr->OutEdges(vid));
Minjie Wang's avatar
Minjie Wang committed
222
223
  });

Minjie Wang's avatar
Minjie Wang committed
224
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphOutEdges_2")
Minjie Wang's avatar
Minjie Wang committed
225
226
227
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
228
    const IdArray vids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
229
    *rv = ConvertEdgeArrayToPackedFunc(gptr->OutEdges(vids));
Minjie Wang's avatar
Minjie Wang committed
230
231
  });

Minjie Wang's avatar
Minjie Wang committed
232
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphEdges")
Minjie Wang's avatar
Minjie Wang committed
233
234
235
236
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const bool sorted = args[1];
237
    *rv = ConvertEdgeArrayToPackedFunc(gptr->Edges(sorted));
Minjie Wang's avatar
Minjie Wang committed
238
239
  });

Minjie Wang's avatar
Minjie Wang committed
240
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphInDegree")
Minjie Wang's avatar
Minjie Wang committed
241
242
243
244
245
246
247
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t vid = args[1];
    *rv = static_cast<int64_t>(gptr->InDegree(vid));
  });

Minjie Wang's avatar
Minjie Wang committed
248
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphInDegrees")
Minjie Wang's avatar
Minjie Wang committed
249
250
251
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
252
    const IdArray vids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
Minjie Wang's avatar
Minjie Wang committed
253
254
255
    *rv = gptr->InDegrees(vids);
  });

Minjie Wang's avatar
Minjie Wang committed
256
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphOutDegree")
Minjie Wang's avatar
Minjie Wang committed
257
258
259
260
261
262
263
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const dgl_id_t vid = args[1];
    *rv = static_cast<int64_t>(gptr->OutDegree(vid));
  });

Minjie Wang's avatar
Minjie Wang committed
264
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphOutDegrees")
Minjie Wang's avatar
Minjie Wang committed
265
266
267
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
Minjie Wang's avatar
Minjie Wang committed
268
    const IdArray vids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
Minjie Wang's avatar
Minjie Wang committed
269
270
    *rv = gptr->OutDegrees(vids);
  });
Minjie Wang's avatar
Minjie Wang committed
271

Minjie Wang's avatar
Minjie Wang committed
272
273
274
275
276
277
278
279
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphVertexSubgraph")
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const IdArray vids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
    *rv = ConvertSubgraphToPackedFunc(gptr->VertexSubgraph(vids));
  });

280
281
282
283
284
285
286
287
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphEdgeSubgraph")
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph *gptr = static_cast<Graph*>(ghandle);
    const IdArray eids = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
    *rv = ConvertSubgraphToPackedFunc(gptr->EdgeSubgraph(eids));
  });

Minjie Wang's avatar
Minjie Wang committed
288
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLDisjointUnion")
289
290
291
292
293
294
295
296
297
298
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    void* list = args[0];
    GraphHandle* inhandles = static_cast<GraphHandle*>(list);
    int list_size = args[1];
    std::vector<const Graph*> graphs;
    for (int i = 0; i < list_size; ++i) {
      const Graph* gr = static_cast<const Graph*>(inhandles[i]);
      graphs.push_back(gr);
    }
    Graph* gptr = new Graph();
Minjie Wang's avatar
Minjie Wang committed
299
    *gptr = GraphOp::DisjointUnion(std::move(graphs));
300
301
302
303
    GraphHandle ghandle = gptr;
    *rv = ghandle;
  });

Minjie Wang's avatar
Minjie Wang committed
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLDisjointPartitionByNum")
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    int64_t num = args[1];
    std::vector<Graph>&& rst = GraphOp::DisjointPartitionByNum(gptr, num);
    // return the pointer array as an integer array
    const int64_t len = rst.size();
    NDArray ptr_array = NDArray::Empty({len}, DLDataType{kDLInt, 64, 1}, DLContext{kDLCPU, 0});
    int64_t* ptr_array_data = static_cast<int64_t*>(ptr_array->data);
    for (size_t i = 0; i < rst.size(); ++i) {
      Graph* ptr = new Graph();
      *ptr = std::move(rst[i]);
      ptr_array_data[i] = reinterpret_cast<std::intptr_t>(ptr);
    }
    *rv = ptr_array;
  });

TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLDisjointPartitionBySizes")
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    const IdArray sizes = IdArray::FromDLPack(CreateTmpDLManagedTensor(args[1]));
    std::vector<Graph>&& rst = GraphOp::DisjointPartitionBySizes(gptr, sizes);
    // return the pointer array as an integer array
    const int64_t len = rst.size();
    NDArray ptr_array = NDArray::Empty({len}, DLDataType{kDLInt, 64, 1}, DLContext{kDLCPU, 0});
    int64_t* ptr_array_data = static_cast<int64_t*>(ptr_array->data);
    for (size_t i = 0; i < rst.size(); ++i) {
      Graph* ptr = new Graph();
      *ptr = std::move(rst[i]);
      ptr_array_data[i] = reinterpret_cast<std::intptr_t>(ptr);
    }
    *rv = ptr_array;
  });
GaiYu0's avatar
cpp lg  
GaiYu0 committed
339
340
341
342
343
344
345
346
347
348
349

TVM_REGISTER_GLOBAL("graph_index._CAPI_DGLGraphLineGraph")
.set_body([] (TVMArgs args, TVMRetValue* rv) {
    GraphHandle ghandle = args[0];
    bool backtracking = args[1];
    const Graph* gptr = static_cast<Graph*>(ghandle);
    Graph* lgptr = new Graph();
    *lgptr = GraphOp::LineGraph(gptr, backtracking);
    GraphHandle lghandle = lgptr;
    *rv = lghandle;
  });
Minjie Wang's avatar
Minjie Wang committed
350
}  // namespace dgl