#include <iostream>
#include <vector>
#include <queue>
using namespace std;

constexpr int INF = 1e8;
constexpr int N_MAX = 100;
constexpr int M_MAX = 500;
bool visited[N_MAX] = {}; 
int n, m;

struct Edge {
    int to_;
    int cost_;
    Edge(int to, int cost) : to_(to), cost_(cost) {}
};

auto clear(vector<vector<Edge>> &g) -> void {
    for (int i = 0; i < N_MAX; ++i) {
        visited[i] = false;
    }

    for(auto& e : g) {
        g.clear();
    }
}

auto prim(vector<vector<Edge>> &g) -> int {
    auto comp = [](auto lhs, auto rhs){return lhs.first > rhs.first;};
    priority_queue<pair<int, int>, vector<pair<int, int>>, decltype(comp)> que(comp);
    int ans = 0;
    que.push(make_pair(0, 0));
    while (!que.empty()) {
        auto p = que.top();
        que.pop();
        if (visited[p.second]) continue;
        visited[p.second] = true;
        auto edges = g[p.second];
        ans += p.first;
        for(const auto &e : edges) {
            if (!visited[e.to_]) {
                que.push(make_pair(e.cost_, e.to_));
            }
        }
    }
    return ans;
}

auto main(int argc, char const *argv[]) -> int {
    while (cin>>n>>m, n || m) {
        vector<vector<Edge>> g(n);
        clear(g);
        for (int i = 0; i < m; ++i) {
            int a, b, cost;
            cin>>a>>b>>cost;
            g[a].push_back(Edge(b, cost));
            g[b].push_back(Edge(a, cost));
        }
        cout<<prim(g)<<endl;
    }
    return 0;
}