#include <bits/stdc++.h>
using namespace std;
const long long undef = -100000;
int n, m;
array<long long, 50> biggest_start_at_least_one;
array<long long, 50> biggest_start;
array<long long, 50> biggest_end_at_least_one;
array<long long, 50> biggest_end;
array<long long, 50> whole;
array<long long, 50> best_ans_in_this_segment;
int main() {
  std::ios_base::sync_with_stdio(false);
  cin >> n >> m;
  for (int i = 0; i < n; ++i) {
    int l;
    vector<long long> input;
    vector<long long> prefix_from_left;
    vector<long long> prefix_from_right;
    vector<long long> dp;
    cin >> l;
    input.resize(l);
    prefix_from_left.resize(l + 1, 0);
    prefix_from_right.resize(l + 1, 0);
    dp.resize(l);
    for (int j = 0; j < l; ++j) cin >> input.at(j);
    for (int j = 1; j <= l; ++j)
      prefix_from_left.at(j) = prefix_from_left.at(j - 1) + input.at(j - 1);
    for (int j = l - 1; j >= 0; --j)
      prefix_from_right.at(j) = prefix_from_right.at(j + 1) + input.at(j);
    biggest_start_at_least_one.at(i) = prefix_from_right.at(0);
    for (int j = 1; j < l; ++j)
      biggest_start_at_least_one.at(i) =
          max(biggest_start_at_least_one.at(i), prefix_from_right.at(j));
    biggest_start.at(i) = max(0LL, biggest_start_at_least_one.at(i));
    biggest_end_at_least_one.at(i) = prefix_from_left.at(l);
    for (int j = l - 1; j > 0; --j)
      biggest_end_at_least_one.at(i) =
          max(biggest_end_at_least_one.at(i), prefix_from_left.at(j));
    biggest_end.at(i) = max(0LL, biggest_end_at_least_one.at(i));
    whole.at(i) = prefix_from_left.at(l);
    dp.at(0) = input.at(0);
    for (int j = 1; j < l; ++j)
      dp.at(j) = max(dp.at(j - 1) + input.at(j), input.at(j));
    best_ans_in_this_segment.at(i) = dp.at(0);
    for (int j = 1; j < l; ++j)
      best_ans_in_this_segment.at(i) =
          max(best_ans_in_this_segment.at(i), dp.at(j));
  }
  long long best_answer = undef;
  long long best_previous_at_least_one = undef;
  long long best_previous = 0;
  for (int i = 0; i < m; ++i) {
    int idx;
    cin >> idx;
    idx -= 1;
    if (best_previous_at_least_one != undef)
      best_answer =
          max(best_answer, best_previous_at_least_one + biggest_end.at(idx));
    if (best_previous != undef)
      best_answer =
          max(best_answer, best_previous + biggest_end_at_least_one.at(idx));
    best_answer = max(best_answer, best_ans_in_this_segment.at(idx));
    best_previous_at_least_one = max(best_previous_at_least_one + whole.at(idx),
                                     biggest_start_at_least_one.at(idx));
    best_previous = max(best_previous + whole.at(idx), biggest_start.at(idx));
  }
  cout << best_answer << endl;
  return 0;
}
